Route Me-iPhone SDK 3.0以降の組み込みのGoogleマップコントロールの代替

画像

松葉杖をねじ込むのではなく、組み込みのカードコントロールの制限に既にうんざりしています。 空白の例:Googleマップアプリはルートを表示する方法を知っていますが、コントロールはその方法を知りません。 地図の上に自分で描く必要があります。

今、私は特定のタスクを持っています:移動したルートとそのエクスポート(共有)の表示を、ささいなGPS速度アプリケーションに追加する必要があります。 私にとっての理由は謎のままです。なぜなら、アプリケーションは平均的であり、一意性は輝いていないからです。

問題に戻ります。 必要な機能はすでに実装されており 、Google Mapsのほとんど機能する松葉杖はすでに作られていますが、これはiPhone SDKのGoogle Mapsに代わるものを明らかにする良いチャンスです。

マット部


カードの公式な管理がなかったときでさえ、私はそのような「代理」と協力しました:

ルートミー:
  1. BSDライセンス(良いか悪いかはあなたが決める)
  2. 多くの地図ソースのサポート:OpenStreetMap、Microsoft Virtual Earth、Cloud Made、Yahoo Maps、その他人気の低いもの
  3. アクティブな開発者コミュニティを形成-Googleグループ

クラウドメイド:
  1. 大規模プロジェクトの一部であり、公式の開発チームがあります(この機会にDimaに挨拶します)。したがって、 Cloud Madeカードとの優れた統合が可能です。
  2. マップの多くのテーマ(色セット)があります
  3. 春に使用され、それはまだ生でした

たとえば、アプリケーションに地図を埋め込み、ユーザーに地図のソースを選択する機会を与えるなど、簡単なことから一連の記事を始めたいと思います。 Route Meが好きです。何よりもCloud Madeを表示できるからです。

準備する

  1. xCodeを開き、新しいプロジェクトを作成します。 ビューベースのアプリケーションを選択し、RouteMeSourceSelectionという名前を付けました
  2. Route Meの最新バージョンをダウンロードする
  3. このガイドで段階的制御を設定する

その後、コンパイルされたプロジェクトが必要です。 問題がある場合は、この例のソースをダウンロードして比較できます

画像

コントロールの追加(コード)


UIViewControllerヘッダー(私の名前は「RouteMeSourceSelectionViewController.h」)を開き、次の操作を行います。
  1. #import "RMMapView.h"
  2. プロトコル「RMMapViewDelegate」を追加します
  3. IBOutlet RMMapView * mapViewを作成します。

画像

メソッド「-(void)viewDidLoad」を再定義します。
- (void)viewDidLoad {
[super viewDidLoad];

[RMMapView class]; // ! . .
[mapView setDelegate:self];
}


コントロールの追加(設計)


  1. Interface Builder(IB)で.xibファイルを開きます
  2. UIView(サブビュー)を既存のUIViewに追加し、RMMapViewとして定義します
  3. IBOutletをUIViewControllerから新しく作成されたRMMapViewに接続します

そのようなテキストを知覚することは難しいことを理解しています。 つまり、次のようになります。
画像

これで、アプリケーションを起動すると、デフォルトのソースであるOpen Open Mapsのマップが表示されます。 私はこれを見ます、私もあなたを願っています:
画像

これはすべて非常に簡単でした。 ユーザーにマップソースを選択する機会を与えましょう。 これを行うには、UIPickerViewコントロールを配置し、UIViewControllerに関連付けます。

マップソース選択用のUIPickerView(コード)


コントローラーヘッダーを開き、2つのプロトコルUIPickerViewDelegateとUIPickerViewDataSource、およびいくつかのIBOutletを追加します。
@interface RouteMeSourceSelectionViewController : UIViewController
<RMMapViewDelegate,
UIPickerViewDelegate, UIPickerViewDataSource>
{
IBOutlet RMMapView *mapView;
IBOutlet UIPickerView *mapSourcePicker;
IBOutlet UIBarButtonItem *mapSettingsBarButton;
}

- (IBAction) showMapsSettings;

@end


次に、UIPickerViewに必要なメソッドをいくつか実装します。 簡単ですが、まだやっていない人には便利です。

static NSArray *titles = nil;

- (NSString *)pickerView:(UIPickerView *)pickerView
titleForRow:(NSInteger)row
forComponent:(NSInteger)component
{
return [titles objectAtIndex:row];
}

- (NSInteger)pickerView:(UIPickerView *)pickerView
numberOfRowsInComponent:(NSInteger)component
{
if (!titles)
{
titles = [[NSArray alloc] initWithObjects:
@"Open Street Maps",
@"Yahoo Map",
@"Virtual Earth Aerial",
@"Virtual Earth Hybrid",
@"Virtual Earth Road",
@"Cloud Made Map",
nil];
}

return [titles count];
}

- (NSInteger)numberOfComponentsInPickerView:(UIPickerView *)pickerView
{
return 1;
}


showMapsSettingsメソッドを作成して、UIPickerViewの表示と非表示、およびいくつかのUIトリックを行います。

- (IBAction) showMapsSettings
{
BOOL toShow = [mapSourcePicker isHidden];

if (toShow)
{
[mapSettingsBarButton setStyle:UIBarButtonItemStyleDone];
}
else // hidding
{
[mapSettingsBarButton setStyle:UIBarButtonItemStyleBordered];
[self setMapSourceWithNumber:[mapSourcePicker selectedRowInComponent:0]];
}

[mapSourcePicker setHidden:![mapSourcePicker isHidden]];
[mapView setUserInteractionEnabled:[mapSourcePicker isHidden]];
}


そして今、最も重要なことは、マップソースを変更する方法です。 注意深く見てみると、「showMapsSettings」で呼び出されていることがわかりました。 ちょっとしたトリックがあります。ソースが変更されてもマップは自動的に更新されないため、シフトして前の位置に戻す必要があります。 これはユーザーには見えません。 最後に、選択したソース番号を一般的なアプリケーション設定に保存します。

#import "RMVirtualEarthSource.h"
#import "RMYahooMapSource.h"
#import "RMCloudMadeMapSource.h"
#import "RMOpenStreetMapsSource.h"

#define CONST_MAP_KEY_bing @""
#define CONST_MAP_KEY_cloud @""

- (void) setMapSourceWithNumber:(int)number
{
if (mapSourceNumber == number)
return;

switch (number) {
case 0:
mapView.contents.tileSource = [[RMOpenStreetMapsSource alloc] init];
break;
case 1:
mapView.contents.tileSource = [[RMYahooMapSource alloc] init];
break;

case 2:
mapView.contents.tileSource = [[RMVirtualEarthSource alloc] initWithAerialThemeUsingAccessKey:CONST_MAP_KEY_bing];
break;
case 3:
mapView.contents.tileSource = [[RMVirtualEarthSource alloc] initWithHybridThemeUsingAccessKey:CONST_MAP_KEY_bing];
break;
case 4:
mapView.contents.tileSource = [[RMVirtualEarthSource alloc] initWithRoadThemeUsingAccessKey:CONST_MAP_KEY_bing];
break;

case 5:
mapView.contents.tileSource = [[RMCloudMadeMapSource alloc] initWithAccessKey:CONST_MAP_KEY_cloud styleNumber:1];
break;

default:
return;
break;
}

// this trick refreshs maps with new source
[mapView moveBy:CGSizeMake(640,960)];
[mapView moveBy:CGSizeMake(-640,-960)];

mapSourceNumber = number;
// remember user choice between runnings
[[NSUserDefaults standardUserDefaults] setInteger:mapSourceNumber forKey:@"mapSourceNumber"];
}


Cloud MadeおよびVirtual Earth(Bing)カードを機能させるには、「開発者APIキー」を取得する必要があります。


最後に追加したいのは、プログラムの起動間のユーザーの選択を記憶することです。 「viewDidLoad」メソッドを変更します。

- (void)viewDidLoad {
[super viewDidLoad];

[RMMapView class];
[mapView setDelegate:self];

int number = [[NSUserDefaults standardUserDefaults] integerForKey:@"mapSourceNumber"];
[self setMapSourceWithNumber:number];
[mapSourcePicker selectRow:mapSourceNumber inComponent:0 animated:NO];
}


マップソース選択用のUIPickerView(デザイン)


IBを開いて:
  1. コントローラーからIBOutletに接続された1つのUIBarButtonItemボタンを持つUIToolbarを追加します
  2. UIBarButtonItemのクリックイベントをshowMapsSettings IBActionに接続します
  3. UIPickerViewをマップの上に追加して非表示にします
  4. UIPickerViewをそのIBOutletに接続し、デリゲートとdataSourceを「ファイルの所有者」として設定します

繰り返しますが、写真は千の言葉を置き換えます。
画像

すべてが正しく行われ、私もあなたも何も忘れていない場合、動作するアプリケーションが表示されます。



表示されたものはすべて、実際のアプリケーションで使用されます。MeetingPoint、無料です。 試してみてください

ここからソースをダウンロード
技術ブログの記事の英語版

コメントに何を追加するか提案してください。この詳細ガイドを展開します。

Source: https://habr.com/ru/post/J79397/


All Articles