音声認識と手書き認識を使ってみよう

2014年6月28日(土)
薬師寺 国安

今回はVS2013から実装された「音声認識」を使ったアプリの作成方法を解説します。音声認識のプロパティについては下記のURLを参照してください。

http://msdn.microsoft.com/en-us/library/windows.media.speechsynthesis.speechsynthesizer.voice.aspx

今回紹介するのはTextBoxに入力された内容を読み上げるサンプルと、手書きで入力した文字を認識して読み上げるサンプルです。

では、例のごとくプロジェクトの作成から始めましょう。プロジェクト名は最初のサンプルでは、「ReadingTextBoxContent」とします。

使用するコントロールは表1の4つのコントロールです。

表1 使用する主なコントロール

コントロール名 名前 役割
MediaElement MediaElement1 文字を読み上げるためのメディア
TextBox contentTextBox 読み上げる内容を入力する入力ボックス
Button readingButton このボタンをクリックすることで、TextBoxの内容を読み上げる
ProgressRing ProgressRing1 音声で読み上げている間リングが回る

では、これらのコントロールをレイアウトしてみましょう。

コントロールのレイアウト

全てをレイアウトすると図1のようになります。

各コントロールをレイアウトした
図1 各コントロールをレイアウトした

書き出されるXAMLをリスト1のように編集します。

リスト1 編集されたXAMLコード(MainPage.xaml)

  • (1) Grid要素をViewBox要素で括る。ViewBoxは伸縮およびスケーリングを実行して単一の子を使用可能な領域全体に引き伸ばすことができるコンテンツ デコレータを定義する要素です。これによって画面の解像度に応じてオブジェクトのサイズも調整されて表示されるようになる。
  • (2)MediaElement要素を配置する。これで音声を発生させる。
  • (3)TextBox要素を配置し、プロパティから「書体」、「文字サイズ」を設定。「AcceptReturn」にチェックを付けて改行の入力を可能にしておく。
  • (4)Button要素を配置する。
  • (5)ProgressRing要素を配置する。音声を読み上げている間、リングが回転する。プロパティの[共通]ペイン内のIsActiveのチェックと、IsEnabledのチェックを外し、使用は不可としておく。IsEnabledはプロパティからなかなか探しにくい、そこで、直接ProgressRing要素に、半角スペースを入れてプロパティを表示させ、その中から選択するといい。その場合はFalseを選択しておく。
<Page
    x:Class="ReadingTextBoxContent.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:ReadingTextBoxContent"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d">
    <Viewbox>■(1)
        <Grid Background="Black" Height="767">
            <StackPanel  HorizontalAlignment="Left" Height="82"  VerticalAlignment="Top" Width="1356" Background="Navy" Orientation="Horizontal">
                <TextBlock HorizontalAlignment="Left" Height="68" Margin="20,15,0,0" TextWrapping="Wrap" Text="音声読み上げ" VerticalAlignment="Top" Width="306" FontSize="48" FontWeight="Bold"/>
<MediaElement x:Name="MediaElement1" Height="35" Margin="0,25,0,0" VerticalAlignment="Top" Width="171"/>■(2)
            </StackPanel>
            <TextBox x:Name="contentTextBox" HorizontalAlignment="Left" Height="579" Margin="23,106,0,0" TextWrapping="Wrap"  VerticalAlignment="Top" Width="1310" FontFamily="Meiryo UI" FontSize="36" AcceptsReturn="True"/>■(3)
            <Button x:Name="readingButton" Content="読み上げ" HorizontalAlignment="Left" Height="70" Margin="20,687,0,0" VerticalAlignment="Top" Width="1313" FontFamily="Meiryo UI" FontSize="36"/>■(4)
        <ProgressRing x:Name="ProgressRing1" HorizontalAlignment="Left" Height="164" Margin="577,358,0,0" VerticalAlignment="Top" Width="197" IsActive="False" IsEnabled="False"/>■(4)
        </Grid>
    </Viewbox>■(1)
</Page>

では、ソリューションエクスプローラー内のMainPage.xamlを展開して、MainPage.xaml.vbをダブルクリックしてコードを記述しましょう。

プログラムコード

Imports Windows.UI.Popups

Public NotInheritable Class MainPage
    Inherits Page

まずは、[読み上げ]ボタンがタップされた時の処理です(リスト2)。

リスト2 [読み上げ]ボタンがタップされた時の処理

入力ボックスに何もデータが入力されていない場合は警告メッセージを表示して、処理を抜ける。それ以外の場合は、以下の処理を行う。MediaElement型のmyMedia変数を宣言し、MediaElement1で初期化しておく。音声機能へのアクセスを提供する、新しいSpeechSynthesizerのインスタンス、synthオブジェクトを作成する。SynthesizeTextToStreamAsyncメソッドで、指定した文字列から、音声出力を非同期に生成する。SetSourceメソッドで、指定されたストリームおよびMIME型を使用してSourceプロパティを設定する。Playメソッドで音声を再生する。ProgressRingの使用を可能にする。これで、音声で読み上げられている間はリングが回る。音声にどんな言語で、どのような声でしゃべらすかは、SpeechSynthesizerのVoiceプロパティで参照できる。先にも書いていたが、下記のURLを参照していただきたい。http://msdn.microsoft.com/en-us/library/windows.media.speechsynthesis.speechsynthesizer.voice.aspx上記URLを見るとJapanese JA は性別が「Female」で、名前は「Haruka」という女性が読み上げるようだ。非同期処理で行われるため、メソッドの先頭にAsyncを追加する。

    Private Async Sub readingButton_Click(sender As Object, e As RoutedEventArgs) Handles readingButton.Click
        If contentTextBox.Text = String.Empty Then
            Dim message As New MessageDialog("読み上げるデータを入力してください。")
            Await message.ShowAsync
         Exit Sub
        Else
            Dim myMedia As MediaElement = Me.MediaElement1
            Dim synth = New Windows.Media.SpeechSynthesis.SpeechSynthesizer
            Dim stream = Await synth.SynthesizeTextToStreamAsync(contentTextBox.Text)
            myMedia.SetSource(stream, stream.ContentType)
            ProgressRing1.IsEnabled = True
            ProgressRing1.IsActive = True
            myMedia.Play()
        End If
    End Sub

次は、音声読み上げが完了した時の処理です(リスト3)。

リスト3 音声読み上げが終わった時の処理

ProgressRingの使用を不可とする。

Private Sub MediaElement1_MediaEnded(sender As Object, e As RoutedEventArgs) Handles MediaElement1.MediaEnded
        ProgressRing1.IsEnabled = False
        ProgressRing1.IsActive = False
    End Sub
End Class

実行すると、図2のように表示されます。もちろん紙面では音声は再生できませんが、ProgressRingが回転しているので、ちゃんと入力した内容を読み上げているのがわかります。

入力した内容を読み上げ、ProgressRingが回転している
図2 入力した内容を読み上げ、ProgressRingが回転している

今回のコードはわずか27行で実装できました。続いて手書きで入力した文字を判別して音声で読み込ませるサンプルを作ってみましょう。

  • 音声認識と手書き認識を行うプログラム

    『Windows ストア アプリ 100行プログラミング』 第9回のサンプルプログラムです。
薬師寺国安事務所

薬師寺国安事務所代表。Visual Basic プログラミングと、マイクロソフト系の技術をテーマとした、書籍や記事の執筆を行う。
1950年生まれ。事務系のサラリーマンだった40歳から趣味でプログラミングを始め、1996年より独学でActiveXに取り組む。1997年に薬師寺聖とコラボレーション・ユニット PROJECT KySS を結成。2003年よりフリーになり、PROJECT KySS の活動に本格的に参加、.NETやRIAに関する書籍や記事を多数執筆する傍ら、受託案件のプログラミングも手掛ける。Windows Phoneアプリ開発を経て、現在はWindows ストア アプリを多数公開中

Microsoft MVP for Development Platforms - Client App Dev (Oct 2003-Sep 2012)。Microsoft MVP for Development Platforms - Windows Phone Development(Oct 2012-Sep 2013)。Microsoft MVP for Development Platforms - Client Development(Oct 2013-Sep 2014)。Microsoft MVP for Development Platforms-Windows Platform Development (Oct 2014-Sep 2015)。

連載バックナンバー

Think ITメルマガ会員登録受付中

Think ITでは、技術情報が詰まったメールマガジン「Think IT Weekly」の配信サービスを提供しています。メルマガ会員登録を済ませれば、メルマガだけでなく、さまざまな限定特典を入手できるようになります。

Think ITメルマガ会員のサービス内容を見る

他にもこの記事が読まれています