Unity公式アセット「Speech-to-Text」の概要と基本的な使い方をまとめました

=====================================
2016/8/28 追記

Asset Storeを見ると、私が書いたときよりバージョンが上がっており、Readmeに以下が追加されていました。


Google non-streaming and Wit.ai non-streaming speech-to-text both rely on UniWeb, which must be manually added to the project

理由不明ですが、UniWebがないと動かないように変わったようです。

ちなみに、UniWebとは、こちらにあるアセットで、Web関係の処理を便利にするものです。$25です。

これまでは、Watson SDKを入れればインポート後のエラーは回避できたのですが、今後は、Watson SDKに加えてUniWebも必要になりました。

Asset Storeのコメントを見ると、Slaghtonという方が、Watson SDKとUniWebをインポートすることで、エラーが消えたと報告されています。


***Update*** installed UniWeb and got the asset working. Keep up the good work!
p.s. for anyone new you need both UniWeb and the Watson SDK for this to work. I think you need windows 8.1+ to.


ということで、今後このアセットを試される場合、UniWebを購入するか、Google Non StreamingやWit.aiを使わず、エラー箇所を自力でコメントアウトすることが必要になります。


バージョン1は、私がブログに残したスクショから2016/8/12と判明しました。バージョン2は2016/8/16ですので、わずか4日で変更されたことになります。

何かライセンスなどで問題があったのかもしれません。

以降は、当時書いた内容と同一です。試せてませんが、UniWebをインポートすれば後はバージョン1と同じ手順で動作確認が可能と思います。

=====================================


先日、Unity Technologiesより、新しいアセット「Speech To Text」が発表されました。


f:id:Takyu:20160815085521j:plain


最近、UWPやHoloLens関連でCortanaを調べていたり、

magicbullet.hatenablog.jp

magicbullet.hatenablog.jp

Androidなど他OSでの音声認識エンジンをUnityで使う方法を調べていたので、せっかくなのでSpeech To Textについても調べてみました。


=================================

目次

1. Speech-to-Textとは?

2. 準備

2-1. アセットインポート

2-2. サービス登録

3. サンプルの動作確認

4. ソースコードの構成

5. その他Tips

6. 終わりに

=================================

1. Speech-to-Textとは?

Unity Technologies社が2016/8/12(現地時間)に公開したアセットです。価格は無料です。

何ができるの?

「SpeechをTextに」という言葉通り、喋った音声をテキストにすることができます。

Provides a wrapper for several speech-to-text solutions and a sample scene that compares text transcriptions from each API.

とあるように、既存の音声認識エンジンをUnityで使えるようにしたアセットです。

サンプルシーンでは、4種類の音声認識エンジンを使って、同時に認識結果を表示できます。

「既存の音声認識エンジン」はどんなもの?

以下の4種類です。

(1) UnityEngine.Windows.Speech

Unity5.4から標準搭載されたエンジンです。

f:id:Takyu:20160815095736j:plain

情報がないのでCortanaとの違いがわかりませんが、WindowsOS用の認識エンジンと思われます。

ネットワークの接続を切ると、下記のようなエラーが出て実行できないため、ネットワーク接続は必須です。

f:id:Takyu:20160815095757p:plain

他エンジンと異なり、唯一API Keyなどの指定が不要です。

ただし、感覚的には認識精度はあまり高くないと感じました。



(2) Google Cloud Speech API


Googleが提供する様々なサービスの総称「Google Cloud Platform(GCP)」の一つです。

マイクから取得した音声を音声データに変換し、それをPOSTすることで、認識結果の文字列をjson形式で受け取ります。

POST用の音声データ変換には、SoX(Sound eXchange)というOSSを使います。

色々見ていると、Pythonでの使い方紹介が多い印象です。

なお、Google Cloud Speech APIは60日までは無償利用可、以後は利用体系に応じて料金がかかります。



(3) IBM Watson Speech to Text

IBMが提供する様々なサービスの総称「Bluemix」の一つです。


[補足]
BluemixとWatsonの関係について明確に書いてある記述がありませんでした。
しかし、IBMのBluemixのサービス一覧紹介サイトに「Watson AlchemyAPI」があり、

アプリ内で自然言語処理とコンピューター・ビジョンを利用して、世界の会話、文書、写真を深く理解できるようにします。

とあるので、Bluemixの一部と解釈しました。


実際、Watson Speech to Textの使用にはBluemixアカウントが必要なので、解釈はそんなにずれてないと思いますが、違っていたらご指摘いただけると助かります。



(4) Wit.ai

botとの会話ができるサービスです。


Wit.aiについては、下記がわかりやすかったです。

bita.jp

上記を参考に解説すると、Wit.aiは、自分で定義した会話文に基づいてシナリオを進行できるサービスです。

なので、記事の中にもある通り、最初に自分でシナリオを定義していく必要があります。


【上記ブログより引用したシナリオの例】

1.「天気教えて?」→bot「オーケーオーケーどこの天気だい?」
2.「ロンドン」(地域はどこでも可)→bot「そこは晴れてるよ」


Wit.aiのHPおよび使い方の解説記事を見ていくと、botとの会話はテキストベースであり、ユーザ側の会話のきっかけにはテキスト入力or音声が選べます。
(今回のUnityアセットは、ここの音声入力のみを使っています)


ところで、蛇足ですが、Wit.aiとあるので、AI(Artificial Intelligence)的な要素はどこだろうと疑問に思ったのですが、上記ブログの最後で定義した言葉と多少ずれても会話ができる、という記載がありました。

また、下記のブログによると、シナリオ作成時に、会話に使えそうな候補を次々出してくれるそうです。


qiita.com

ということで、私はこの辺りがAIと解釈しました。

2. 準備

2-1. アセットインポート

(注) Unityのバージョンが5.4以上である必要があります。

2-1-1. Watson SDK

まずはUnityでプロジェクトを作り、アセットストアからSpeech-to-Textを入手してインポートします。

インポートすると、いきなり多数のエラーが出ます。

f:id:Takyu:20160815095906p:plain


これはWatson Developer Cloud Unity SDKが入っていないためで、ReadmeにもWatsonサイトから入手してください、という記載があります。

SDKはここから入手できます。

github.com

2016/8/15時点では、unity-sdk-0.3.0.zipが最新版でした。

これを解凍するとunity-sdkというフォルダが生成されるので、Watsonというフォルダ名に変更します。

中身はこのようになっています。

f:id:Takyu:20160815100633p:plain

このWatsonフォルダをAssets直下にコピーします。ここまで進めると、Unityプロジェクトのフォルダ構成はこのようになり、先ほどのエラーが消えます。

f:id:Takyu:20160815101126j:plain

なお、Watson SDKをインポートすると、さらに新しいエラーがでます。

f:id:Takyu:20160815101617p:plain

これは、TouchScriptというアセットがないので削除します、というエラーです。

TouchScriptがなくてもシーン実行ができるし、TouchScriptは今回のアセットの機能とは関係ないため、このまま続けて大丈夫です。


ちなみに、WatsonSDKは、Speech-to-Textアセットのスクリプトの中で呼ばれています。

そのため、もしWatsonを使わない場合であっても、

・とりあえずSDKをインポートする

・関連部分を全部コメントアウトする

のどちらかが必要です。

2-1-2. SoX

SoXとは、Sound eXchangeという音声ファイル変換ツール(コマンド)です。

元々Linux系の中で有名なコマンドですが、Windows系でも使えるようになっています。

今回はここから14.4.2を入手しました。

sourceforge.net

入手したsox-14.4.2-win32.zipを解凍し、Assets/StreamingAssetsフォルダの中に、新しくThirdParty/SoX/Windowsというフォルダを作ります。

ここにsox-14.4.2-win32フォルダの中身をそのまま入れます。

f:id:Takyu:20160815103031p:plain


これで、インポート作業は完了です。


2-2. サービス登録

使いたいサービスに登録します。ここは先ほどのインポート時とは異なり、使わないサービスは登録しなくても大丈夫です。

なお、今回の検証では、このアセットが音声からテキスト変換する既存サービスのWrapperということがわかったので、IBM Watsonの検証は実施しませんでした。

そのため、Watsonのサービス登録や動作確認はできていませんが、本ブログの2-1の作業が終わっていれば、Google Speech APIと同様の手順により、APIusername/passwordを取得すれば動作すると思います。


2-2-1. Google Cloud Speech API (Non Streamingの場合)

(1) まずはサイトにアクセスし、「コンソールへ移動」をクリックします。

cloud.google.com


f:id:Takyu:20160815104040j:plain

(2) Googleアカウントでログインすると、ポータル画面が表示されます。ここで、API Managerを選択します。

f:id:Takyu:20160815104309p:plain


(3) 検索フォームで「Speech」と入力します。Google Cloud Speech APIが検索候補に出てくるので選択します。

f:id:Takyu:20160815104429p:plain

(4) 画面中心の上付近で「有効にする」を選択します。
(下記の画像は「有効にする」を選択後なので「無効にする」と表示されていますが)

f:id:Takyu:20160815104547p:plain


(5) 続けて、認証情報の登録を行います。下記の画面から「認証情報に進む」を選択します。

f:id:Takyu:20160815104946p:plain

指示に従って登録していきます。

APIを呼び出す場所、については、色々な種類がありましたが、今回は「その他のUI」を選択しました。


f:id:Takyu:20160815105214p:plain

次は APIキーを生成します。今回は名称をTestとしました。

リクエストを受けるサーバ IPアドレスについては、とりあえず空欄でも大丈夫です。


APIキーが生成されたら、Unityに戻ります。Hierarchy Viewの

Canvas/ SpeechToTextServiceWidgets/ GoogleNonStreamingSpeechToText にあるコンポーネントAPI Keyをコピペします。

f:id:Takyu:20160815105411p:plain

これで、Google Speech APIをNonStreamingで使用する準備が完了です。

2-2-2. Google Cloud Speech API (Streamingの場合)


Google Cloud Speech APIAPI Keyを登録すると、ポータル画面に「認証情報」という項目が追加されます。

これをクリックすると、このように認証情報を作成する画面が出てくるので、「サービスアカウントキー」を選択します。

f:id:Takyu:20160815110111p:plain

すると、

・ App Engine default service account
・ Compute Engine default service account

という二種類の形式を選択する画面になります。それぞれの違いは調べられていませんが、今回のサンプル検証ではApp Engineを選択して動作しました。

キーファイルはjsonとP12と二種類の形式が選択できますが、今回はJSON形式を選択します。

処理を進めていくと、json形式の証明書ファイルを入手できます。
(ブラウザ設定を変えていなければ、Downloadフォルダに生成されます)

このファイルの名称をcredentials.jsonと変更し、Unity側の

Assets/StreamingAssets/GoogleStreamingSpeechToTextProgram

のフォルダにインポートします。

f:id:Takyu:20160815110755p:plain


これで、Google Speech APIをStreamingで使用する準備が完了です。

2-2-3. Wit.ai

Wit.aiのサイトにアクセスします。

f:id:Takyu:20160815111228j:plain

githubFacebookでログインし、表示されたポータル画面の右上にある"+"マークを選択して、New Appを選択します。

f:id:Takyu:20160815111439p:plain

App作成画面になるので、名称、公開範囲を設定して + Create Appします。

f:id:Takyu:20160815111612j:plain


続けて、作成したApp画面の右上付近にあるSettingsを選択します。

f:id:Takyu:20160815111754p:plain

表示されたページの真ん中付近にある、API DetailsにServer Access Tokenという項目があります。

ここで表示されている文字列をコピーします。

f:id:Takyu:20160815112148p:plain

あとは、Unity側で、

f:id:Takyu:20160815112401p:plain

Canvas/ SpeechToTextServiceWidgets/ WitAiNonStreamingSpeechToTextのコンポーネントAccess Tokenを指定すれば完了です。

3. サンプルの動作確認

[前提]

・インターネットに接続されている

・マイクが接続されている

なお、動作確認は、

Windows 10 Pro
・Unity 5.4.0f3 Personal

で実施しました。


speechToTextComparison.unityを開き、シーン実行して、「Start Recording」というボタンを押してから好きな言葉をしゃべってみると、このように、複数のエンジンを同時に使って結果を比較できます。


現時点だと、Google Speech APIが日本語対応できてないのと、Watsonの検証をしていないですが、Wit.aiの精度が一番高いように見えます。

4. ソースコードの構成

サンプルシーンを使って、簡単ですが動きを見てみます。

f:id:Takyu:20160815114329p:plain

まず、画面構成についてです。

サンプルシーンはこのように左上の"Start Recording"というボタン、左側のテキスト、右側の6つのScroll Viewから構成されています。

左側のテキストは認識精度を高めるためのオプションのようですが、日本語では意味がなさそうなので今回は使っていません。


では動きを説明します。

Start Recordingボタンを押すと、音声取得状態になります。

このとき、SpeechToTextCpomparisonWidgetクラスでは

OnRecordButtonClicked()
→StartRecording()

のように呼ばれます。

StartRecording()はこのような処理が実行されています。

f:id:Takyu:20160815114737p:plain

foreachの中にある、m_SpeechToTextServiceWidgetsという変数は、それぞれのサービスオブジェクトであり、

serviceWidget.StartRecording();

によって、各サービスで音声認識処理を開始しています。

各サービスは、いずれもSpeechToTextServiceクラスを継承しており、StreamingかNonStreamingかでさらに継承の対象が異なります。

クラス間の関係図をまとめるとこうなります。

f:id:Takyu:20160815122456p:plain


また、きれいに描けてないですが、メソッドの呼び出しはこのような関係図になります。

f:id:Takyu:20160815122504p:plain


5. その他Tips

5-1. 対応OSは?

Readmeには、Windows OS環境で動く、と書かれています。

Webサービスなので、本来他のOSで動かないということはないですが、たとえば今回のGoogle Speech APIを使用するために、それぞれ認識対象の音声ファイルをSoXで作成しています。

これはOS依存なので、このままではiOSAndroidでは動かず、基本的にWindows限定と考えるのがよさそうです。
(SoXMac版の提供もあるので、Macでも動くかもしれません)

Watsonはわかりませんが、Wit.aiについても、Google Speech APIの処理と同じ処理で音声ファイルを取得しているので、SoX依存の可能性があります。


そのため、基本的にはWindows(Mac)用と考えたほうがよさそうです。


5-2. Streaming と Non Streamingの違いは?

一般的かはわかりませんが、ここでは下記の意味で使われていました。

Streaming :
Start Recordingボタンを押してから指定時間(default:15sec)の間に認識した言葉を、逐次テキストで表示する

Non Streaming :
Recordingボタンを押してから指定時間経過後かStop Recordingボタンを押すまで音声を録音し、録音終了後にサービスに問い合わせして、認識結果をテキストで表示する


そのため、Non Streamingを使うと、Recordingが終わるまでは画面が変化せず、終了後数秒経ってから初めて画面に認識結果が表示されます。


5-3. 使わないサービスを無効化する方法は?

使用しないサービスは、Canvas/SpeechToTextComparisonWidget オブジェクトのコンポーネントから調整できます。

たとえば、今回私はWatsonは使わなかったので、下記のようにSpeech To Text Service Widgetの配列Sizeを6から4に変更し、Watsonオブジェクトを外しました。

f:id:Takyu:20160815103536p:plain

シーン上では6つのScroll Viewが出たままになりますが、Watsonのサービスを使わなくてもエラーなく実行可能です。

5-4. Google Speech APIを日本語化する方法は?

現時点で不明です。Unity側のソースコードではロケール指定がなさそうでした。
一方、Google Speech APIのポータルでも、言語設定に関する設定項目を見つけることができませんでした。

ただ、Pythonベースで試された方は、日本語のテキストを表示できていたので、本来は日本語対応していると思われます。

私もまだコードや設定項目を詳しく見たわけではないので、見つけられたらここに追記したいと思います。


6. 終わりに

このアセットは、あくまで音声をテキストに変える、という機能をUnityで使うためのWrapperです。

各サービスはそれ以外の機能もたくさんありますが、このアセットの目的と異なるので、当然それらをUnityで使うことはできません。

個人的には、音声認識のためだけに各サービスを新規契約するのは、オーバースペックな印象を持ちました。


今回のアセットを調べた動機の一つに、別途Android向け音声認識をUnityで使う方法を調べていたというのがあります。

今回のアセット「Speech-to-Text」は、モバイル用途ではなさそうなので、自分が調べていた方法は引き続き活用できそうです。

Android系の音声認識をUnityで使う方法については、まとめたら別途ブログにしたいと思います。