はじめに
マイクから生データを受信するには、クラスが責任を負います
android.media.AudioRecord
android.media.AudioRecord
。 内部バッファにデータを書き込むため、定期的にデータを収集する必要があります。
コンストラクター
オブジェクトを作成するには、次を指定する必要があります。
audioSource | 録音はどこから来ましたか? 私たちの場合、これ MediaRecorder.AudioSource.MIC |
---|
sampleRateInHz | ヘルツのサンプルレート。 ドキュメントは、44100Hzがすべてのデバイスでサポートされていると主張しています |
---|
channelconfig | チャネル構成 たぶん CHANNEL_IN_MONO CHANNEL_IN_MONO または CHANNEL_IN_STEREO CHANNEL_IN_STEREO モノはどこでも動作します。
重要:これらの定数は、それらが示すチャネルの数と一致しません。 このパラメーターに1または2を渡すことはできません。
|
---|
audioFormat | コーデックとしてよく知られている入力データ形式。 たぶん ENCODING_PCM_16BIT ENCODING_PCM_16BIT または ENCODING_PCM_8BIT
|
---|
bufferSizeInBytes | 同じ内部バッファのサイズ。 それから、オーディオストリームを読み取ることができます。 読み取り部分のサイズはこの値を超えないようにしてください。 このパラメーターの最小許容値は、次の方法で取得できます getMinBufferSize() getMinBufferSize() 。
|
---|
オブジェクトは、作成中に必要なシステムリソースを取得しようとします。 彼がどれだけ成功したか、関数を呼び出すことで見つけることができます
getState()
getState()
。 彼女が戻ったら
STATE_INITIALIZED
STATE_INITIALIZED
、その後、すべてが正常である場合、
STATE_UNINITIALIZED
STATE_UNINITIALIZED
は、エラーが発生したことを意味します。
エラーの原因は2つあります。小さすぎるバッファーと無効なフォーマットです。 1つ目は
、 getMinBufferSize()
呼び出す
ことで回避すること
getMinBufferSize()
。 第二に、実際、彼による。
getMinBufferSize()
この静的メソッドは、
AudioRecord
オブジェクトが機能する内部バッファーの最小サイズを生成します。 パラメーターは、コンストラクターと同じ意味を持ちます。 書き込みにこの特定の値を使用することはお勧めできません。 システムがまだ何かでビジーである場合、プログラムはまだ行のすべてのデータを読み取る時間がない可能性があり、レコードに穴があります。 私は、サイズを10倍大きくするようアドバイスしました。
リスト形式
getMinBufferSize()
メソッドには素晴らしい機能があります-
このデバイスに対して無効なパラメーターを誓う
ため 、
ERROR_BAD_VALUE
ERROR_BAD_VALUE
または
ERROR
ERROR
つまり、考えられるすべての組み合わせを調べて、デバイスがサポートしている形式を見つけることができます。
たとえば、次のように:
int[] rates = {8000, 11025, 22050,44100, 48000, 96000 }; int[] chans = {AudioFormat.CHANNEL_IN_MONO, AudioFormat.CHANNEL_IN_STEREO}; int[] encs = {AudioFormat.ENCODING_PCM_8BIT, AudioFormat.ENCODING_PCM_16BIT}; for(int enc : encs) { for(int ch : chans) { for(int rate : rates) { int t = AudioRecord.getMinBufferSize(rate, ch, enc); if((t != AudioRecord.ERROR) && (t != AudioRecord.ERROR_BAD_VALUE)) {
データ読み取り
内部バッファからデータを取得するには、メソッドを使用します
read()
read()
。 次の3つのバージョンがあります。
read(byte[] audioData, int offsetInBytes, int sizeInBytes)
read(short[] audioData, int offsetInShorts, int sizeInShorts)
read(ByteBuffer audioBuffer, int sizeInBytes)
それらのパラメーター:
audioData | データが書き込まれる配列 |
---|
audioBuffer | データが書き込まれるバッファ |
---|
offsetInBytes / offsetInShorts | 記録を開始するインデックス |
---|
sizeInShorts | 要求されたデータブロックのサイズ。 ByteBuffer およびbyte[] 単位、 short[] 短整数byte[] |
---|
すべてが正常であれば、メソッドは
ByteBuffer
または
byte[]
バリアントである場合、または
short[]
短整数を読み取る場合、読み取られたバイト数を返します。 呼び出し時にオブジェクトが正しく初期化されていなかった場合、
ERROR_INVALID_OPERATIONを
返し 、パラメーターに何か問題がある場合
-ERROR_BAD_VALUE重要:メソッドは、要求された量のデータを読み取るまで呼び出しスレッドをブロックします。 内部バッファーに十分な数がない場合、
read()
はマイクから来るまで待機します。 したがって、メソッドは
別のスレッドから呼び出す必要があります。そうしないと、アプリケーションがハングします。
アプローチ、リトリート、固定
プログラムがマイクからデータを受信できるように、AndroidManifestのxmlファイルで適切な解像度を指定する必要があります。
<uses-permission android:name="android.permission.RECORD_AUDIO" />
記録を開始するには、メソッドを呼び出す必要があります
startRecording()
startRecording()
、そして終了する-
stop()
stop()
。 録音は何度でも開始および停止できます。
オブジェクトの処理が完了したら、メソッドを呼び出す必要があります
release()
release()
。 オブジェクトによってキャプチャされたすべてのシステムリソースを解放します。 その後、オブジェクト
は使用
できず 、オブジェクト
を参照する変数を
null
に設定する必要があり
null
。
重要:これら3つのメソッドは、前述のメソッドとは異なり、スローされます
IllegalStateException
IllegalStateException
、それらが初期化されていない(つまり... ...)オブジェクトに対して、または間違った順序で呼び出された場合。 したがって、それらは「慎重に」処理する必要があります。
try
ブロックを介して。
使用例
以下のクラスは、上記のすべてを実行します。 さらに、彼は彼に登録済みを送ります
Handler
受信したデータに関する
Handler
メッセージ。 このデータは別のスレッドで処理されるため、まだ処理されていないデータを新しいデータで上書きしないように、循環バッファーが使用されます。
コードは
AudioFormatInfo
クラスを使用します。 これは、記録フォーマットを記述する3つのフィールドを持つ
POJOです:
sampleRateInHz
、
audioFormat
および
audioFormat
package com.MyCompany; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import android.media.AudioFormat; import android.media.AudioRecord; import android.media.MediaRecorder; import android.os.Handler; import android.os.Process;