我想捕捉音频从Android设备。下面我的code似乎已成功使SD卡上的 WAV 的文件,但它不能播放。我试着用不同的媒体播放器,但没有工作,发挥它。有一个在我的code,是造成这一问题的问题。
code
公共类MainActivity扩展ActionBarActivity { 私有静态最后弦乐LOG_TAG =AudioRecordTest; 静态最终诠释AUDIO_PORT = 2048; 静态最终诠释SAMPLE_RATE = 8000; 静态最终诠释SAMPLE_INTERVAL = 20; //毫秒 静态最终诠释SAMPLE_SIZE = 2;每个样本//字节 静态最终诠释BUF_SIZE = SAMPLE_INTERVAL * SAMPLE_INTERVAL * SAMPLE_SIZE * 2; 私有静态诠释[] = mSampleRates新INT [] {44100,44056,47250,48000,22050,16000,11025,8000}; 私人主题recordingThread = NULL; 私人布尔isRecording = FALSE; INT BufferElements2Rec = 1024; //想打2048(2K),因为2个字节,我们 //仅使用1024 INT BytesPerElement = 2; // 2字节的16位格式 私人诠释缓冲区大小; 私人AudioRecord记录; @覆盖 保护无效的onCreate(捆绑savedInstanceState){ super.onCreate(savedInstanceState); 的setContentView(R.layout.activity_main); 的StartRecording(); } @覆盖 公共布尔onCreateOptionsMenu(菜单菜单){ //充气菜单;如果是present这增加了项目操作栏。 。getMenuInflater()膨胀(R.menu.main,菜单); 返回true; } 私人无效的startRecording(){ 录音机= findAudioRecord(); recorder.startRecording(); isRecording = TRUE; recordingThread =新主题(新的Runnable(){ 公共无效的run(){ writeAudioDataToFile(); } },AudioRecorder线程); recordingThread.start(); } //转换短字节 私人字节[] short2byte(短[] SDATA){ INT shortArrsize = sData.length; 字节[]字节=新的字节[shortArrsize * 2]; 的for(int i = 0; I< shortArrsize;我++){ 字节[我* 2] =(字节)(SDATA [1] - 安培;设为0x00FF); 字节[(我* 2)+ 1] =(字节)(SDATA [Ⅰ]≥→8); SDATA [I] = 0; } 返回字节; } 公共AudioRecord findAudioRecord(){ 对于(INT率:mSampleRates){ 对于(短AudioFormat的:新的短[] {AudioFormat.ENCODING_PCM_8BIT,AudioFormat.ENCODING_PCM_16BIT}){ 对于(短channelConfig:新的短[] {AudioFormat.CHANNEL_IN_MONO,AudioFormat.CHANNEL_IN_STEREO}){ 尝试{ Log.d(LOG_TAG,试图率+速度+赫兹,位:+ AudioFormat的+,声道: + channelConfig); BUFFERSIZE = AudioRecord.getMinBufferSize(速率,channelConfig,AudioFormat的); 如果(缓冲区大小!= AudioRecord.ERROR_BAD_VALUE){ //检查是否我们可以实例,有一个成功 记录=新AudioRecord(MediaRecorder.AudioSource.DEFAULT,速度,channelConfig,AudioFormat的,缓冲区大小); 如果(recorder.getState()== AudioRecord.STATE_INITIALIZED) 返回记录; } }赶上(例外五){ Log.e(LOG_TAG,房价+异常,继续努力。E); } } } } 返回null; } 私人无效writeAudioDataToFile(){ / * //写字节输出音频 短SDATA [] =新的短[BufferElements2Rec] 而(isRecording){ //获取声音输出麦克风字节格式 recorder.read(SDATA,0,BufferElements2Rec); 的System.out.println(短wirting到文件+ sData.toString()); // //存储声音缓冲区 字节BDATA [] = short2byte(SDATA); sendLiveAudio(BDATA); } * / 字符串文件路径=/sdcard/test.wav; 短SDATA [] =新的短[BUFFERSIZE / 2]; FileOutputStream中OS = NULL; 尝试{ OS =新的FileOutputStream(文件路径); }赶上(FileNotFoundException异常五){ e.printStackTrace(); } 而(isRecording){ //获取声音输出麦克风字节格式 recorder.read(SDATA,0,缓冲区大小/ 2); Log.d(ERAY,短wirting到文件+ sData.toString()); 尝试{ // //从写入缓冲区文件中的数据 // //存储声音缓冲区 字节BDATA [] = short2byte(SDATA); os.write(BDATA,0,缓冲区大小); }赶上(IOException异常五){ e.printStackTrace(); } } 尝试{ os.close(); }赶上(IOException异常五){ e.printStackTrace(); } } 私人无效STO precording(){ //停止记录活动 如果(NULL!=录像机){ isRecording = FALSE; recorder.stop(); recorder.release(); 记录= NULL; recordingThread = NULL; } } @覆盖 公共布尔onOptionsItemSelected(菜单项项){ //处理动作栏项目点击这里。操作栏会 //自动处理上点击主页/向上按钮,只要 //你在AndroidManifest.xml中指定一个父活动。 INT ID = item.getItemId(); 如果(ID == R.id.action_settings){ 返回true; } 返回super.onOptionsItemSelected(项目); } @覆盖 公共无效onBack pressed(){ super.onBack pressed(); STO precording(); }}
解决方案
试试这个.....
公共类Audio_Record延伸活动{私有静态最终诠释RECORDER_SAMPLERATE = 8000;私有静态最终诠释RECORDER_CHANNELS = AudioFormat.CHANNEL_IN_MONO;私有静态最终诠释RECORDER_AUDIO_ENCODING = AudioFormat.ENCODING_PCM_16BIT;私人AudioRecord记录= NULL;私人主题recordingThread = NULL;私人布尔isRecording = FALSE;@覆盖公共无效的onCreate(捆绑savedInstanceState){ super.onCreate(savedInstanceState); 的setContentView(R.layout.main); setButtonHandlers(); enableButtons(假); INT缓冲区大小= AudioRecord.getMinBufferSize(RECORDER_SAMPLERATE, RECORDER_CHANNELS,RECORDER_AUDIO_ENCODING);}私人无效setButtonHandlers(){ ((按钮)findViewById(R.id.btnStart))setOnClickListener(btnClick)。 ((按钮)findViewById(R.id.btnStop))setOnClickListener(btnClick)。}私人无效enableButton(INT ID,布尔isEnable){ ((按钮)findViewById(ID))的setEnabled(isEnable)。}私人无效enableButtons(布尔isRecording){ enableButton(R.id.btnStart,isRecording!); enableButton(R.id.btnStop,isRecording);}INT BufferElements2Rec = 1024; //想打2048(2K),因为2个字节,我们只用1024INT BytesPerElement = 2; // 2字节的16位格式私人无效的startRecording(){ 记录=新AudioRecord(MediaRecorder.AudioSource.MIC, RECORDER_SAMPLERATE,RECORDER_CHANNELS, RECORDER_AUDIO_ENCODING,BufferElements2Rec * BytesPerElement); recorder.startRecording(); isRecording = TRUE; recordingThread =新主题(新的Runnable(){ 公共无效的run(){ writeAudioDataToFile(); } },AudioRecorder线程); recordingThread.start();} //转换短字节私人字节[] short2byte(短[] SDATA){ INT shortArrsize = sData.length; 字节[]字节=新的字节[shortArrsize * 2]; 的for(int i = 0; I< shortArrsize;我++){ 字节[我* 2] =(字节)(SDATA [1] - 安培;设为0x00FF); 字节[(我* 2)+ 1] =(字节)(SDATA [Ⅰ]≥→8); SDATA [I] = 0; } 返回字节;}私人无效writeAudioDataToFile(){ //写字节输出音频 字符串文件路径=/sdcard/voice8K16bitmono.pcm; 短SDATA [] =新的短[BufferElements2Rec] FileOutputStream中OS = NULL; 尝试{ OS =新的FileOutputStream(文件路径); }赶上(FileNotFoundException异常五){ e.printStackTrace(); } 而(isRecording){ //获取声音输出麦克风字节格式 recorder.read(SDATA,0,BufferElements2Rec); 的System.out.println(短wirting到文件+ sData.toString()); 尝试{ // //从写入缓冲区文件中的数据 // //存储声音缓冲区 字节BDATA [] = short2byte(SDATA); os.write(BDATA,0,BufferElements2Rec * BytesPerElement); }赶上(IOException异常五){ e.printStackTrace(); } } 尝试{ os.close(); }赶上(IOException异常五){ e.printStackTrace(); }}私人无效STO precording(){ //停止记录活动 如果(NULL!=录像机){ isRecording = FALSE; recorder.stop(); recorder.release(); 记录= NULL; recordingThread = NULL; }}私人View.OnClickListener btnClick =新View.OnClickListener(){ 公共无效的onClick(视图v){ 开关(v.getId()){ 案例R.id.btnStart:{ enableButtons(真); 的StartRecording(); 打破; } 案例R.id.btnStop:{ enableButtons(假); STO precording(); 打破; } } }};@覆盖公共布尔的onkeydown(INT键code,KeyEvent的事件){ 如果(键code == KeyEvent.KEY code_BACK){ 完(); } 返回super.onKeyDown(键code,事件);}}
I want to capture audio from an Android device. My code below seems to successfully make a wav file on the SD card but it cannot be played. I tried to play it using different media players but none work. There is an issue in my code that is causing this problem.
code
public class MainActivity extends ActionBarActivity {
private static final String LOG_TAG = "AudioRecordTest";
static final int AUDIO_PORT = 2048;
static final int SAMPLE_RATE = 8000;
static final int SAMPLE_INTERVAL = 20; // milliseconds
static final int SAMPLE_SIZE = 2; // bytes per sample
static final int BUF_SIZE = SAMPLE_INTERVAL * SAMPLE_INTERVAL * SAMPLE_SIZE * 2;
private static int[] mSampleRates = new int[]{44100, 44056, 47250, 48000, 22050, 16000, 11025, 8000};
private Thread recordingThread = null;
private boolean isRecording = false;
int BufferElements2Rec = 1024; // want to play 2048 (2K) since 2 bytes we
// use only 1024
int BytesPerElement = 2; // 2 bytes in 16bit format
private int bufferSize;
private AudioRecord recorder;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
startRecording();
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
private void startRecording() {
recorder = findAudioRecord();
recorder.startRecording();
isRecording = true;
recordingThread = new Thread(new Runnable() {
public void run() {
writeAudioDataToFile();
}
}, "AudioRecorder Thread");
recordingThread.start();
}
// convert short to byte
private byte[] short2byte(short[] sData) {
int shortArrsize = sData.length;
byte[] bytes = new byte[shortArrsize * 2];
for (int i = 0; i < shortArrsize; i++) {
bytes[i * 2] = (byte) (sData[i] & 0x00FF);
bytes[(i * 2) + 1] = (byte) (sData[i] >> 8);
sData[i] = 0;
}
return bytes;
}
public AudioRecord findAudioRecord() {
for (int rate : mSampleRates) {
for (short audioFormat : new short[]{AudioFormat.ENCODING_PCM_8BIT, AudioFormat.ENCODING_PCM_16BIT}) {
for (short channelConfig : new short[]{AudioFormat.CHANNEL_IN_MONO, AudioFormat.CHANNEL_IN_STEREO}) {
try {
Log.d(LOG_TAG, "Attempting rate " + rate + "Hz, bits: " + audioFormat + ", channel: "
+ channelConfig);
bufferSize = AudioRecord.getMinBufferSize(rate, channelConfig, audioFormat);
if (bufferSize != AudioRecord.ERROR_BAD_VALUE) {
// check if we can instantiate and have a success
recorder = new AudioRecord(MediaRecorder.AudioSource.DEFAULT, rate, channelConfig, audioFormat, bufferSize);
if (recorder.getState() == AudioRecord.STATE_INITIALIZED)
return recorder;
}
} catch (Exception e) {
Log.e(LOG_TAG, rate + "Exception, keep trying.", e);
}
}
}
}
return null;
}
private void writeAudioDataToFile() {
/*// Write the output audio in byte
short sData[] = new short[BufferElements2Rec];
while (isRecording) {
// gets the voice output from microphone to byte format
recorder.read(sData, 0, BufferElements2Rec);
System.out.println("Short wirting to file" + sData.toString());
// // stores the voice buffer
byte bData[] = short2byte(sData);
sendLiveAudio(bData);
}*/
String filePath = "/sdcard/test.wav";
short sData[] = new short[bufferSize / 2];
FileOutputStream os = null;
try {
os = new FileOutputStream(filePath);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
while (isRecording) {
// gets the voice output from microphone to byte format
recorder.read(sData, 0, bufferSize / 2);
Log.d("eray", "Short wirting to file" + sData.toString());
try {
// // writes the data to file from buffer
// // stores the voice buffer
byte bData[] = short2byte(sData);
os.write(bData, 0, bufferSize);
} catch (IOException e) {
e.printStackTrace();
}
}
try {
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
private void stopRecording() {
// stops the recording activity
if (null != recorder) {
isRecording = false;
recorder.stop();
recorder.release();
recorder = null;
recordingThread = null;
}
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
@Override
public void onBackPressed() {
super.onBackPressed();
stopRecording();
}
}
解决方案
Try This.....
public class Audio_Record extends Activity {
private static final int RECORDER_SAMPLERATE = 8000;
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 Thread recordingThread = null;
private boolean isRecording = false;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
setButtonHandlers();
enableButtons(false);
int bufferSize = AudioRecord.getMinBufferSize(RECORDER_SAMPLERATE,
RECORDER_CHANNELS, RECORDER_AUDIO_ENCODING);
}
private void setButtonHandlers() {
((Button) findViewById(R.id.btnStart)).setOnClickListener(btnClick);
((Button) findViewById(R.id.btnStop)).setOnClickListener(btnClick);
}
private void enableButton(int id, boolean isEnable) {
((Button) findViewById(id)).setEnabled(isEnable);
}
private void enableButtons(boolean isRecording) {
enableButton(R.id.btnStart, !isRecording);
enableButton(R.id.btnStop, isRecording);
}
int BufferElements2Rec = 1024; // want to play 2048 (2K) since 2 bytes we use only 1024
int BytesPerElement = 2; // 2 bytes in 16bit format
private void startRecording() {
recorder = new AudioRecord(MediaRecorder.AudioSource.MIC,
RECORDER_SAMPLERATE, RECORDER_CHANNELS,
RECORDER_AUDIO_ENCODING, BufferElements2Rec * BytesPerElement);
recorder.startRecording();
isRecording = true;
recordingThread = new Thread(new Runnable() {
public void run() {
writeAudioDataToFile();
}
}, "AudioRecorder Thread");
recordingThread.start();
}
//convert short to byte
private byte[] short2byte(short[] sData) {
int shortArrsize = sData.length;
byte[] bytes = new byte[shortArrsize * 2];
for (int i = 0; i < shortArrsize; i++) {
bytes[i * 2] = (byte) (sData[i] & 0x00FF);
bytes[(i * 2) + 1] = (byte) (sData[i] >> 8);
sData[i] = 0;
}
return bytes;
}
private void writeAudioDataToFile() {
// Write the output audio in byte
String filePath = "/sdcard/voice8K16bitmono.pcm";
short sData[] = new short[BufferElements2Rec];
FileOutputStream os = null;
try {
os = new FileOutputStream(filePath);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
while (isRecording) {
// gets the voice output from microphone to byte format
recorder.read(sData, 0, BufferElements2Rec);
System.out.println("Short wirting to file" + sData.toString());
try {
// // writes the data to file from buffer
// // stores the voice buffer
byte bData[] = short2byte(sData);
os.write(bData, 0, BufferElements2Rec * BytesPerElement);
} catch (IOException e) {
e.printStackTrace();
}
}
try {
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
private void stopRecording() {
// stops the recording activity
if (null != recorder) {
isRecording = false;
recorder.stop();
recorder.release();
recorder = null;
recordingThread = null;
}
}
private View.OnClickListener btnClick = new View.OnClickListener() {
public void onClick(View v) {
switch (v.getId()) {
case R.id.btnStart: {
enableButtons(true);
startRecording();
break;
}
case R.id.btnStop: {
enableButtons(false);
stopRecording();
break;
}
}
}
};
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_BACK) {
finish();
}
return super.onKeyDown(keyCode, event);
}
}