AudioRecorder无法正确录制

时间:2014-06-20 12:35:35

标签: android audio timer

我正在尝试使用AudioRecorder记录某个时间间隔的wav文件(对应于一定数量的样本)。停止录制我使用Timer().schedule(delay)一段时间后停止。但无论该延迟的值是多少,文件总是大小相同,而且不可读。

public class Record extends Activity {
private static final int RECORDER_SAMPLERATE = 44100;
int compt=0;
int duration=1;
//int numSample= duration*RECORDER_SAMPLERATE;
private static final int RECORDER_CHANNELS = AudioFormat.CHANNEL_IN_MONO;

private static final int RECORDER_AUDIO_ENCODING = AudioFormat.ENCODING_PCM_16BIT;
private AudioRecord recorder = null;
private volatile Thread recordingThread=null;
private volatile boolean isRecording = false;

int bufferSize = AudioRecord.getMinBufferSize(RECORDER_SAMPLERATE,RECORDER_CHANNELS, RECORDER_AUDIO_ENCODING); 
long mySubChunk1Size = 16;
short myBitsPerSample= 16;
int myFormat = 1;
int myChannels = 1;
long myByteRate =RECORDER_SAMPLERATE* myChannels * myBitsPerSample/8;
int myBlockAlign = myChannels * myBitsPerSample/8;
Handler handler;
String filePath = Environment.getExternalStorageDirectory().getAbsolutePath()+"/recordedSound"+compt+".wav";
DataOutputStream dd;

@Override
public void onCreate(Bundle savedInstanceState)  {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_raw_rec);
    try
    {
        try {

            startRec();

        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        new Timer().schedule(new TimerTask()
        {
            @Override
            public void run()
            {

                recordingThread.interrupt();
                recordingThread=null;
                isRecording=false;
                recorder.stop();
                recorder.release();
                recorder = null;



            }

        }
        ,5000); //execute after 5 seconds of recording

    }//end try
    catch(IllegalStateException e) {
        e.printStackTrace();
    }

}


private void startRec() throws IOException{
    recorder = new AudioRecord(MediaRecorder.AudioSource.MIC,RECORDER_SAMPLERATE, RECORDER_CHANNELS,RECORDER_AUDIO_ENCODING, bufferSize);

    recorder.startRecording();


    isRecording = true;
    recordingThread = new Thread(new Runnable() {
        public void run() {
            writeToFile();
        }
    }, "AudioRecorder Thread");
    recordingThread.start();

}




private void writeToFile() {
    // Write the output audio in byte

    byte[] data= new byte[bufferSize];


    while (isRecording) {
        try{
            recorder.read(data, 0, bufferSize);
            Log.d("recorder value", "value"+recorder);
        }
        catch (NullPointerException e)
        {
            e.printStackTrace();
        }
        try {
            // // writes the data to file from buffer
            // // stores the voice buffer
            dd=new DataOutputStream( new FileOutputStream(filePath));

            dd.writeBytes("RIFF");
            dd.writeInt(0); // Final file size not known yet, write 0 
            dd.writeBytes("WAVE");
            dd.writeBytes("fmt ");
            dd.writeInt(Integer.reverseBytes(16)); // Sub-chunk size, 16 for PCM
            dd.writeShort(Short.reverseBytes((short) 1)); // AudioFormat, 1 for PCM
            dd.writeShort(Short.reverseBytes( (short) myChannels));// Number of channels, 1 for mono, 2 for stereo
            dd.writeInt(Integer.reverseBytes(RECORDER_SAMPLERATE)); // Sample rate
            dd.writeInt(Integer.reverseBytes( (RECORDER_SAMPLERATE*myBitsPerSample*myChannels/8))); // Byte rate, SampleRate*NumberOfChannels*BitsPerSample/8
            dd.writeShort(Short.reverseBytes((short) (myChannels*myBitsPerSample/8))); // Block align, NumberOfChannels*BitsPerSample/8
            dd.writeShort(Short.reverseBytes( myBitsPerSample)); // Bits per sample
            dd.writeBytes("data");
            dd.write(data);
            //dd.close();

        } catch (IOException e) {

            e.printStackTrace();
        }
    }

}
我在做错了什么?

1 个答案:

答案 0 :(得分:1)

您正在while的{​​{1}}循环的每次迭代中创建新的WAV文件。

更好的方法是将PCM数据缓冲区(没有任何标头)写入临时文件。并确保只创建writeToFile一次。
然后,当录制结束时,生成RIFF标头并将其写入目标WAV文件,然后写入临时文件的内容。