Reputation: 425
My problem is really simple: I'm using a MediaRecorder
to record voice while the user is pressing on a FAB, and playing it afterwards (when he/she releases). The issue is that I lose a few seconds near the end of the recording, and I can't figure out why (they never get played back). Code (only relevant parts are shown):
Variables
double record_length = 0;
boolean recording = false;
String outputFile;
Handler myHandler = new Handler();
MediaRecorder recorder = new MediaRecorder();
OnTouchListener
findViewById(R.id.record_record).setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_DOWN) {
findViewById(R.id.delete_swipe).setVisibility(View.VISIBLE);
StartRecord();
} else if (event.getAction() == MotionEvent.ACTION_UP) {
if(recording){
EndRecord();
}
findViewById(R.id.delete_swipe).setVisibility(View.INVISIBLE);
}
return true;
}
});
.
public void StartRecord() {
recording = true;
record_length = 0;
SharedPreferences saved_login = getSharedPreferences("FalloundLogin", 0);
recorder.setAudioSource(MediaRecorder.AudioSource.MIC);
recorder.setOutputFormat(MediaRecorder.OutputFormat.THREE_GPP);
recorder.setAudioEncoder(MediaRecorder.OutputFormat.AMR_NB);
//removed construction of outputFile, but it is generated correctly - I checked
recorder.setOutputFile(outputFile);
try {
recorder.prepare();
recorder.start();
} catch (IOException e) {
e.printStackTrace();
}
myHandler.postDelayed(UpdateUploadLength, 200);
}
.
public void EndRecord() {
recording = false;
try {
recorder.stop();
recorder.reset();
recorder = null;
} catch (IllegalStateException e) {
e.printStackTrace();
}
MediaPlayer m = new MediaPlayer();
try {
m.setDataSource(outputFile);
} catch (IOException e) {
e.printStackTrace();
}
try {
m.prepare();
} catch (IOException e) {
e.printStackTrace();
}
m.start();
}
I need the recording to be a maximum of 27 seconds. To avoid complications, I tested without this extra termination condition and am including the Runnable
just for completeness.
private Runnable UpdateUploadLength = new Runnable(){
@Override
public void run() {
if(recording == true) {
record_length += 0.2;
if (record_length < 27) {
myHandler.postDelayed(UpdateUploadLength, 200);
} else {
//TODO: stop recording
myHandler.removeCallbacks(UpdateUploadLength);
}
}
};
I've been trying for a few hours with no luck, so any help is appreciated (also - and I dunno if it's bad to ask multiple questions in the same post - but is there any way to get better audio quality from MediaRecorder
?)
Thanks in advance.
Upvotes: 0
Views: 433
Reputation: 3029
Its answear for your second question. Yes you can have much better quality. There is more encoding types, file formats and parameters in library. Example:
mediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4);
mediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AAC);
mediaRecorder.setAudioSamplingRate(44100);
mediaRecorder.setAudioEncodingBitRate(256000);
this code will set your recorder to m4a files with AAC, 44,1kHz sampling rate and around 256kbps
Upvotes: 1