掲載 | 『JAVA PRESS』Vol.8 |
---|---|
概要 | Java プログラムの操作性を向上させる標準 API について紹介。 |
Java プログラムの評判の悪さは、ユーザインタフェースに対して手間を惜しんだ プログラムが多いことも要因のひとつになっています。そこでこの記事では、 より使いやすいプログラムを作るのに役立つ、 Java Accessibility、JavaHelp、Java Speech という 3 つの 標準 API を紹介しました。
記事中に、次のような誤りがありました。お詫びして訂正します。
JLabel label = "アドレス:";
JLabel label = new JLabel("アドレス:");
void testEngineState(long)
boolean testEngineState(long)
Java Speech API の節で詳しく書けなかった、音声エンジンの状態管理について 補足したいと思います。
記事中でも触れたとおり、Java Speech では
エンジンの状態を long
値 (64 ビット整数) の各ビットに意味を与えることで
管理しています。具体的な値は、音声エンジンを表すそれぞれのインタフェースで、
次のように定義されています (大きな表なので、ブラウザによっては
うまく表示されないかもしれません)。
javax.speech.Engine インタフェース |
||||||||
---|---|---|---|---|---|---|---|---|
DEALLOCATED | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000001 |
ALLOCATING_RESOURCES | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000010 |
ALLOCATED | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000100 |
DEALLOCATING_RESOURCES | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00001000 |
PAUSED | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000001 | 00000000 |
RESUMED | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000010 | 00000000 |
javax.speech.synthesis.Synthesizer インタフェース |
||||||||
QUEUE_EMPTY | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000001 | 00000000 | 00000000 |
QUEUE_NOT_EMPTY | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000010 | 00000000 | 00000000 |
javax.speech.recognition.Recognizer インタフェース |
||||||||
LISTENING | 00000000 | 00000000 | 00000000 | 00000001 | 00000000 | 00000000 | 00000000 | 00000000 |
PROCESSING | 00000000 | 00000000 | 00000000 | 00000010 | 00000000 | 00000000 | 00000000 | 00000000 |
SUSPENDED | 00000000 | 00000000 | 00000000 | 00000100 | 00000000 | 00000000 | 00000000 | 00000000 |
FOCUS_ON | 00000000 | 00000001 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 |
FOCUS_OFF | 00000000 | 00000010 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 | 00000000 |
この表は、64 ビットの値を実際に 2 進数で表したものです。8 ビットずつ考えると、 これらの値は 5 つのグループに分かれていることが見て取れます。
最初のグループは、下から 8 ビットを使っている 4 つの値で、
エンジンに対するリソース割り当ての状態を表します。Java Speech では、
これを DEALLOCATED
(解放済み)、
ALLOCATING_RESOURCES
(割り当て中)、
ALLOCATED
(割り当て済み)、
DEALLOCATING_RESOURCES
(解放中) の 4 つに分けているわけです。
エンジン (Engine
オブジェクト) を生成した時点では、
まだリソースが割り当てられておらず、DEALLOCATED
になっています。
ついで、Engine
の allocate()
メソッドを呼び出すと、
リソース割り当てが開始され、ALLOCATING_RESOURCES
になり、
無事完了すると ALLOCATED
になります。音声処理が終わって
エンジンが不要になったら、プログラムから deallocate()
メソッドを
呼び出します。するとエンジンの状態は DEALLOCATING_RESOURCES
になり、
リソースの解放が完了すると DEALLOCATED
に戻ります。
2 つめのグループは、同じ Engine
インタフェース
の PAUSED
および RESUMED
です。これはそれぞれ、
pause()
メソッドで処理を停止した状態と、
resume()
メソッドで処理を開始した状態を表します。
エンジンを起動してリソースを割り当てた状態では PAUSED
ですから、
処理を行うときには resume()
で開始する必要があります。
音声処理が必要ない場合は、こまめに pause()
で処理を停止すると、
マシンやプログラムにかかる負荷が小さくなります。
続く 3 つめのグループは、Synthesizer
インタフェースで
定義された QUEUE_EMPTY
および QUEUE_NOT_EMPTY
です。
文字どおり、音声合成エンジンの出力キューが空かそうでないかを表しています。
Java Speech では、音声合成エンジンに依頼した処理はキューに貯えられ、
順番に処理されていきます。これによって、音声が重なることを防いでいるわけです。
この 2 つの値を使えばそれを調べることができます。
ついで 4 つめのグループ は、
音声認識エンジン (Recognizer
オブジェクト) の処理状態を表します。
ユーザが喋るのを待っている LISTENING
、喋った内容を処理している
段階を表す PROCESSING
、認識に使う文法の変更などで
一時的に停止した状態を表す SUSPENDED
の 3 つがあり、
3 つめのグループ同様、処理の段階に応じて自動的に変わります。
最後のグループは、音声認識エンジンが音声フォーカスを
持っているかどうかを表します。FOCUS_ON
ならそのエンジンが
フォーカスを持っており、FOCUS_OFF
なら他のエンジンが
持っていることになります。音声認識を利用するプログラムでは、これも可能な限り
こまめにフォーカスの管理を行うべきです。たとえ自分のプログラムでは 1 個所しか
音声認識を使っていなくても、ハンディキャップのあるユーザは
別のユーザ補助機能を使っているかもしれません (記事の「Java Accessibility API」の
節を参照してください)。
実際のエンジンでは、これらの値を合わせたもの (論理和、OR) で 状態が表されます。ただし、各グループ内で複数の値がオンになることは ありません (3 つめのグループで考えるとわかりやすいでしょう)。
また、グループによっては、ある特定の状況にならないと意味がないものもあります。
例えば、ALLOCATED
に
ならなければ PAUSED
か RESUMED
かは意味を持たず、
さらにこれが RESUMED
になって
はじめて Synthesizer
や Recognizer
インタフェースで
定義された状態に意味が出るわけです。
なお、記事中の表 3 では、Engine
インタフェース
のうち getEngineState()
、testEngineState(long)
、
waitEngineState(long)
の 3 つを「状態の調査」と分類しています。
getEngineState()
はその時点の状態値を取得するものです。
testEngineState(long)
はある状態になっていれば true
、
でなければ false
を返すメソッドで、
//合成エンジンのキューが空かどうか調べる boolean b = testEngineState(Synthesizer.QUEUE_EMPTY);
のように使います。waitEngineState(long)
も引数の与え方は
同じですが、引数で指定した状態まで実行がブロックされるというものです。
記事中で使ったプログラムのソースコードをダウンロードしていただけます。 シフト JIS で、改行コードは CRLF です。