[iOS 10] SiriKitでメッセージ送信アプリを作成してみた 〜”たこ焼き”でメッセージ送って!〜(その2)

2016.09.14

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

1 はじめに

前回に引き続き、iOS 10で使用可能になったSiriKitを使用したメッセージ送信アプリ「たこ焼き」の作成をすすめます。

「たこ焼き」とは、常に決まっている特定の相手にメッセージを送信するアプリです。 メッセージ送信には、「宛先」・「宛先グループ」・「本文」の諸元が有りますが、このうち「本文」以外は常に一定なので、「本文」だけを伝えれば、直ちにメッセージを送信できます。

前回の記事をご覧になっていない方は、是非、こちらを先にご参照下さい。
[iOS 10] SiriKitでメッセージ送信アプリを作成してみた 〜”たこ焼き”でメッセージ送って!〜(その1)

2 UI Extension

(1) ビューの表示

最初に、ExtensionSampleUIの方のinfo.plistにもINSendMessageIntentが指定されていることを確認したのですが、実は、この時点でExtensionUIの方も動作しています。

試しに、ExtensionSampleUIのストーリーボードで、UIImageを貼り付け、画像を表示してみます。 013

すると、それが反映されていることを確認できます。

011

(2) インタラクティブ要素の禁止

上の例でわかるように、ここでのビューは、通常のビューと何も変わらないので、例えば、ボタンや、テキスト入力などのインタラクティブ要素を追加することは可能ですが、これらは厳密には禁止されており、ユーザーがそれを操作することは出来ません。

3 宛先不要

”たこ焼きのメッセージをどなたに送信しますか?”と言う風に、Siriはメッセージ送信のインテントを作成するために、メッセージの本文や宛先を聞き取ろうとしています。

最初に説明したとおり「たこ焼き」は、特定の相手にメッセージを送るアプリなので、宛先は必要ありません。

そこで、宛先に関するバリデーションを行う、resolveRecipients(forSendMessage:with:)メソッドを次のように変更します。

// Implement resolution methods to provide additional information about your intent (optional).
func resolveRecipients(forSendMessage intent: INSendMessageIntent, with completion: @escaping ([INPersonResolutionResult]) -> Void) {
    let notRequired = INPersonResolutionResult.notRequired()
    completion([notRequired])
}

こうすることで、Siriは、「たこ焼き」用のメッセージ送信インテントを作成する際に。宛先を聞こうとしなくなります。

「たこ焼きで今日遅くなりますってメッセージ送って」と話しかけると、次のようになります。

015

4 メッセージ送信の実装

「送信」ボタンを押すか、「送信して」と話しかけると、handle(sendMessage:completion:)メソッドに処理が移ります。 パラメータであるintentに「本文」が入っていますので、ここで実際のメール送信を行えば完了です。

func handle(sendMessage intent: INSendMessageIntent, completion: @escaping (INSendMessageIntentResponse) -> Void) {

    // ここにメッセー送信のロジックを記述する

    let userActivity = NSUserActivity(activityType: NSStringFromClass(INSendMessageIntent.self))
    let response = INSendMessageIntentResponse(code: .success, userActivity: userActivity)
    completion(response)
}

handle(sendMessage:completion:)からの戻り値であるINSendMessageIntentResponseで.successを送ると、Siriは、送信が成功したことを認識し、「送信しました」と話しながら、画面下記のようになります。

016

5 メール本文をUIで表示する

(1) メール本文の削除

ExtensionSampleUIのストーリーボードで作成した画面の下には、Siriによってメッセージの本文が表示されています。

014

これを消すためには、まず、IntentViewControllerに、INUIHostedViewSiriProvidingプロトコルを追加しdisplaysMessage(:Bool)メソッドで true を返します。

//class IntentViewController: UIViewController, INUIHostedViewControlling {
class IntentViewController: UIViewController, INUIHostedViewControlling, INUIHostedViewSiriProviding {

    //・・・省略・・・

    var displaysMessage: Bool {
        return true
    }

ここまでの作業で、下部の表示はなくなります。

(2) メール本文のUIでの表示

続いて、UIでメール本文を表示出来るように、ストーリーボードでラベルを置きます。 017

そして、confirm(sendMessage:completion:)メソッドで、ラベルに文字をセットします。

func configure(with interaction: INInteraction!, context: INUIHostedViewContext, completion: ((CGSize) -> Void)!) {

    let intent = interaction.intent as! INSendMessageIntent
    label.text = intent.content

    //・・・省略・・・

結果は、次のようになります。

018

6 最後に

今回は、新しく利用可能になったSiriKitについて試してみました。まだ、分からな事だらけですが、少しづつ慣れていくしか無いのかなという感じです。

なお、今回は、端末にインストールして確認するところまでしか実施していませんが、ドキュメントでは、CapabilitiesでSiriをONにするように書かれていましたので、ストアに申請する際は、必須になるのかも知れません。

019

コードは、下記に置きました。
github [GitHub] https://github.com/furuya02/SiriKitSample

7 参考にさせて頂いたリンク


Siri + Apps
SiriKit Programming Guide
Introducing SiriKit
Extending Your Apps with SiriKit


イラストは、イラストAC 様のものを利用させて頂きました