Skip to content

ApplicationManual

Ryo Mizuno edited this page Mar 31, 2016 · 2 revisions

目次

本ドキュメントは、Device Connect と連携するUIアプリの作成について網羅するチュートリアルです。
読者がiOSそしてObjective-Cに関する一般的な知識を保持している事を前提に解説していきます。

Device Connect とは、RESTfulコンセプトを用いて通信先への命令送信や、通信元と通信先の間でのデータ送受信を可能とするプロトコルです。
各処理にはProfileという形でURIが割り振られ、そのURIに対しHTTPでアクセスしたり、AndroidやiOSなどのプラットフォーム毎に定められたメッセージ通信プロトコルでアクセスしたりする事で処理を行います。

また Device Connect におけるデバイスプラグインとは、Device Connect プロトコルに従ったリクエストメッセージを受け取って解釈し、実デバイスに対し適切な処理を行わせ、得られた結果を Device Connect プロトコルに従ったレスポンスメッセージとして返却する様な、デバイスとのやり取りを実質的に担うモジュールとなります。

本ドキュメントで扱う用語について記載します。

用語 意味
UIアプリ Device Connect が提供する機能を、UIを使ってユーザーに提供することを目的として作られたアプリケーションの総称。
標準プロファイル Device Connect において機能別に定義されたAPI群のカテゴリー。例えば下記のような標準プロファイルが存在します。
Service Discovery: 稼働している Device Connect デバイスプラグインによって検知された、デバイスプラグイン対応周辺機器の一覧を取得します。
Vibration: デバイスプラグイン対応周辺機器の振動機能を提供します。

まず事前にチュートリアルのソースコード一式をダウンロードしてください。

また、このチュートリアルでは依存関係解決フレームワーク CocoaPods を利用して外部のソースコードを取得するようにしています。
そのため、以下のコマンドをターミナルで実行し、CocoaPods CLIツールをインストールする必要があります:

$ sudo gem install cocoapods

このチュートリアルで特に取り扱う物は以下の通りです:

  1. dConnectSDKForIOS
  2. dConnectDeviceHostPlugin
  3. NativeAppTutorial

1つめの dConnectSDKForIOS は、デバイスプラグインやUIアプリで必要となる Device Connect のフレームワークやバンドルを提供しています。

2つめの dConnectDeviceHostPlugin は、Device Connect デバイスプラグインの1つのiOS Hostデバイスプラグインであり、ローカルのiOSデバイスを制御することができます。また、このデバイスプラグインは Device Connect のほぼ全ての共通プロファイルを実装しているという特徴があります。

そして3つめの NativeAppTutorial は、次章「Get Started」で取り扱うサンプルUIアプリのXcodeプロジェクトとなります。

このチュートリアルの最後でカバーする、デバイスプラグインを用いてiOSデバイスの加速度情報を取得するパートでは、iOSシミュレーターではなくiOS実機が必要となります。
iOS実機へのアプリ転送は Apple の開発者登録が必要である点にご注意ください。

このチュートリアルを終える頃には簡単な Device Connect 対応UIアプリの作成方法に関する知識が身に付きます。
もし Device Connect デバイスプラグイン対応デバイスがお手元にあるのでしたら、Device Connect 対応UIアプリで対応デバイスに様々な処理を行わせてみると楽しいかもしれません。

Device Connect のUIアプリを作成するには、中核となるSDK、そして最低でも1つのデバイスプラグインをUIアプリに組み込む必要があります。
幸い、iOS版 Device Connect は CocoaPods を利用してUIアプリが簡単に Device Connect を導入できるようにしています。

4章で提供したチュートリアルのソースコードには Device Connect のUIアプリ開発環境が既に整備されています。
Device Connect 開発における最終的な終着点、開発を行う為に必要な物事を把握していただくためにも、さっそく中を覗いてみましょう。

それでは NativeAppTutorial のXcodeプロジェクトに何が含まれているのか確認してみましょう。

プロジェクトナビゲーター

まず、プロジェクトナビゲーターの「DeviceConnectUIAppTutorial」グループの下にはソースコード「AppDelegate」および「ViewController」、Storyboard「Main」が含まれています。
これらソースが本チュートリアルで扱うUIアプリのロジックやUIを定義することになります。

次に「Frameworks」グループの下を見てみましょう。
「libPods」という静的ライブラリは CocoaPods が提供するライブラリで、そのビルドおよびリンクの際に dConnectSDKForIOS や dConnectDeviceHostPlugin もビルドされ、UIアプリにリンクされます。

最後にプロジェクトのルートにある「Podfile」ですが、これは CocoaPods のファイルで、このファイルの中でこのプロジェクトが dConnectSDKForIOS や dConnectDeviceHostPlugin に依存していることを記述しています。
CocoaPods はこのファイルを元に、このプロジェクトの依存関係を解決してくれます。

まず最初に、CocoaPods を用いて依存関係の解決を行って、dConnectSDKForIOS や dConnectDeviceHostPlugin をUIアプリに組み込んでみましょう。

では、ターミナルを開き、cdコマンドでこのUIアプリの Podfile があるディレクトリに移動してください。そして以下の CocoaPods コマンドを実行してください:

$ pod install --verbose

Device Connect のソースコードが Github からダウンロードされるので、少し時間がかかります。

実行が完了すると、ディレクトリ内に「DeviceConnectUIAppTutorial.xcworkspace」というワークスペースが生成されているはずです。以降の作業はプロジェクト「DeviceConnectUIAppTutorial.xcodeproj」で行うのではなく、このワークスペースから行うようにしてください。

それでは、ワークスペースを開いてみましょう。
ビルドや起動の手順について説明しますが、既にこの段階でこのチュートリアルのUIアプリをビルドして起動するまでの準備は整っています。
さっそくUIアプリのビルドおよび起動を実際に行ってみましょう。

ワークスペース上で、XcodeのRunボタンを押してUIアプリのビルドおよび起動を行ってください。
順を追って内容を説明します:

  1. Device Connect において、Local OAuth という認証機構によりセキュリティが担保されています。まずは「クライアント登録」ボタンを押してこのUIアプリを Local OAuth に登録してください。



2. UIアプリの認可と登録が済んだら、アクセストークンの取得を行ってください。
アクセストークンとはUIアプリの身元を証明する情報であり、UIアプリから特定プロファイルへのアクセスを可能にする情報となります。
アクセストークン取得の際、UIアプリが用いようとしている標準プロファイルなどをユーザーが認可する為の画面が開くので認可してください。
本UIアプリは通知を行う Notification と、加速度などの取得を行う Device Orientation、2つの標準プロファイルの認可を求めてきます。


3. 「デバイス検索」ボタンを押して Service Discovery プロファイルを用いたデバイス検索を行い、iOS Host デバイスプラグインの対応端末、すなわち今操作中のUIアプリがインストールされた手元のiOSデバイス(iOS実機やiOSシミュレーターなど)を検出します。


4. アクセストークンを添えてiOS Hostデバイスプラグインの Notification プロファイルにアクセスし、通知ダイアログの表示要求を行います。
この際、iOS Hostデバイスプラグインが用いるプロファイルをユーザーが認可する為の画面が開くので認可してください。
認可をするとiOS Hostデバイスプラグイの Notification プロファイルへ通知の表示要求が届き、実際に通知が表示されます。



5. 最後に、アクセストークンを添えてiOS Hostデバイスプラグインの Device Orientation プロファイルにアクセスし、加速度センサーやジャイロセンサーからの情報をイベントとして継続的に受け取る要求をします。
受け取りに成功すると、「acceleration」の箇所にiOSデバイスの加速度がリアルタイムで表示されます。

上記の5つのプロセスがこのUIアプリの動作となります。
ユーザーに Device Connect 対応UIアプリを提供する際は、なるべくこの5つのプロセスを経る形で Device Connect へのアクセスを促してください。

では次の章で先述の5つのプロセスを実行するにあたり、UIアプリ側で行っていた処理の解説に移ります。

UIアプリが行う事は主に、Device Connect の中核として処理・管理を行う「Device Connect マネージャー」に対してのリクエスト送信・レスポンス受信、そしてイベント受領用コールバックの指定です。

では、5.2章で触れたUIアプリの5プロセスのうち第4プロセスで行った Notification プロファイルに関するリクエスト送信・レスポンス受信のコードを見てみましょう。
プロジェクトの ViewController.m の関数 - (BOOL)callNotificationAPI:(NSString *)serviceId のリクエスト生成部分が以下のコードになります。

DConnectRequestMessage *request = [[DConnectRequestMessage alloc]init];
[request setAction: DConnectMessageActionTypePost];
[request setApi: @"gotapi"];
[request setProfile: DConnectNotificationProfileName];
[request setAttribute: DConnectNotificationProfileAttrNotify];
[request setServiceId: serviceId];
[request setAccessToken: _accessToken];

[request setInteger: DConnectNotificationProfileNotificationTypeMail
             forKey: DConnectNotificationProfileParamType];
[request setString: @"notification message"
            forKey: DConnectNotificationProfileParamBody];

「DConnectRequestMessage」は Device Connect iOS Message APIでリクエストを送信する際に使われるクラスです。
基本的に、リクエストには以下のパラメータを指定します:

  1. HTTP の GET・POST・PUT・DELETE メソッドのどれを用いるか(setAction)
  2. 基本APIは何か(setApi、標準では "gotapi" を指定する)
  3. アクセスするプロファイル・インターフェース・アトリビュートは何か(setProfile, setInterface, setAttribute)
  4. アクセスするデバイスのIDは何か(setServiceId、Service Discovery プロファイルで検索して取得したもの)
  5. アクセストークンは何か(setAccessToken)

その上で各種プロファイルのドキュメントで記述されている通りにパラメータを設定する事でリクエストが完成します(setIntegerやsetStringなど)。
そして最後にリクエストを Device Connect マネージャーに送信し、レスポンスを受信します。

DConnectManager *mgr = [DConnectManager sharedManager];
[mgr sendRequest: request callback:^(DConnectResponseMessage *response) {
    NSLog(@"mgr request(callback)");
    if (response != nil) {
        NSLog(@" - response is not null");
        NSLog(@" - response - result: %d", [response result]);
        if ([response result] == DConnectMessageResultTypeOk) {
            NSString *notificationId =
                [response stringForKey: DConnectNotificationProfileParamNotificationId];
            NSLog(@" - response - OK notificationId: %@", notificationId);
            result = YES;
        } else {
            NSLog(@" - response - errorCode: %d", [response errorCode]);
        }
    }

    /* Wait解除 */
    dispatch_semaphore_signal(semaphore);
}];

Device Connect マネージャー(DConnectManager)はシングルトンで、それのインスタンスに対してリクエストを渡し、そのリクエストに対するレスポンスを Apple のC言語拡張である block (^(){})で受け取っています。
iOSネイティブアプリからリクエストを送信しパラメータを受信するプロセスはこの様になりますので、リクエストを送信したいプロファイルのAPIに応じて DConnectRequestMessage に設定するパラメータを適切に変更してください。

では次に、5.2章で触れたUIアプリの5プロセスのうち第5プロセスで行った Device Orientation プロファイルに関するリクエスト送信・レスポンス受信のコードを見てみましょう。
プロジェクトの ViewController.m の関数 - (IBAction) onDeviceOrientaionEvent: (id)sender のイベント登録およびイベントメッセージ受領コールバックの設定が以下のコードになります。

[[DConnectEventHelper sharedHelper]registerEventWithRequest: request
                 responseHandler: ^(DConnectResponseMessage *response)
{
    dispatch_async(dispatch_get_main_queue(), ^{
        NSString *message = nil;
        if ([response result] == DConnectMessageResultTypeOk) {
            message = @"処理成功しました。";
        } else {
            message = @"処理失敗しました。";
        }
        [deviceOrientationInfo setText: [NSString stringWithFormat: @"event: %@", message]];
    });
}
                  messageHandler:^(DConnectMessage *message)
{
    dispatch_async(dispatch_get_main_queue(), ^{
        DConnectMessage *orientation =
            [message messageForKey: DConnectDeviceOrientationProfileParamOrientation];
        DConnectMessage *acceleration =
            [orientation  messageForKey: DConnectDeviceOrientationProfileParamAcceleration];

        double x = [acceleration doubleForKey: DConnectDeviceOrientationProfileParamX];
        double y = [acceleration doubleForKey: DConnectDeviceOrientationProfileParamY];
        double z = [acceleration doubleForKey: DConnectDeviceOrientationProfileParamZ];

        [deviceOrientationEventInfo setText:
            [NSString stringWithFormat: @"acceleration: x=%.1lf, y=%.1lf, z=%.1lf", x, y, z]];
    });
}];

DConnectEventHelperの関数 -registerEventWithRequest:responseHandler:messageHandler: がイベント周りの処理を引き受けています。
特に、messageHandler:の引数にするblockは、非同期で送信されてくるイベントメッセージの受け口になるので、イベントメッセージを受け取った際の挙動はそのblockに記述する事になります。

Device Connect は様々なデバイスに対して共通のプロトコルでアクセス・制御することを可能にする規格ではありますが、ユーザエクスペリエンスがデバイスの特色・機能により変化することに留意しなければなりません。

ですからユーザエクスペリエンスを向上する為にも、開発者の皆様がプロファイル毎の機能、リクエストそしてレスポンスの詳細に関し、RESTful / iOS Message / Android Intent API などのドキュメントに目を通し、仕様を把握することをお勧めします。
そしてUIアプリの操作対象とするデバイスの特色・機能に応じ、UIアプリのデザインを変えることを推奨します。

dConnectDeviceSphero をアプリ側で使用する場合は、Build Settings で以下の項目を設定する必要があります。

  • [Architectures]
    • [$(ARCHS_STANDARD_32_BIT)]
  • [Enable Bitcode]
    • No

そして、「Supporting Files」フォルダにある「{{アプリ名}}-Info.plist」ファイルに以下のように「Supported external accessory protocols」に「com.orbotix.robotprotocol」属性を追加しなければいけません。

dConnectDevicePebble をアプリ側で使用する場合は、「Supporting Files」フォルダにある「{{アプリ名}}-Info.plist」アイルに以下のように「Supported external accessory protocols」に「com.getpebble.public」属性を追加しなければいけません。

Clone this wiki locally