According to Android SDK MediaRecorder.setCamera can be used to recycle the existing camera instance for video capture and preview without resetting the preview. I was not able to find any sample, and all my attempts were futile: I either get the wrong state exception, or MediaRecorder.prepare fails.
For reference: http://developer.android.com/reference/android/media/MediaRecorder.html#setCamera(android.hardware.Camera)
I ran into the same problem and found out how it can work. Some things have to be done correctly. First you should check the state chart from the android document.
A working order of commands is as follows.
mCamera = Camera.open();
rec = new MediaRecorder(); // state "Initial"
mCamera.lock();
mCamera.unlock();
rec.setCamera(mCamera); // state still "Initial"
rec.setVideoSource(MediaRecorder.VideoSource.CAMERA); // state "Initialized"
rec.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4); // state "DataSourceConfigured"
rec.setVideoEncoder(MediaRecorder.VideoEncoder.H264);
rec.setPreviewDisplay(surfaceHolder.getSurface());
rec.setOutputFile(Environment.getExternalStorageDirectory() + "/test.mp4");
rec.prepare(); // state "Prepared"
rec.start(); // state "Recording"
// ...
rec.stop(); // state "Initial"
A full example can be found here.
The Android Camera app source provides the best example. After some investigation, I discovered that recorder.setCamera(camera) should be called immediately after instantiation of the MediaRecorder, or at least before any settings are applied to it. Applying any settings (setVideoSource(), etc.) before calling setCamera() results in an error.
I got hint from @lyron.
First, open the front camera.
int cameraId = -1;
int camNums = Camera.getNumberOfCameras();
for( int i = 0 ; i < camNums ; i++) {
CameraInfo info = new CameraInfo();
Camera.getCameraInfo(i, info);
if( info.facing == CameraInfo.CAMERA_FACING_FRONT ) {
cameraId = i;
break;
}
}
mCamera = Camera.open(cameraId);
mCamera.unlock();
I need to use the front camera as above.
And DON'T FORGET to UNLOCK the camera.
If you don't, you'll see errors below.
E/MediaRecorder(15509): start failed: -19
E/SampleVideoRecorder(15509): Exception :
E/SampleVideoRecorder(15509): java.lang.RuntimeException: start failed.
E/SampleVideoRecorder(15509): at android.media.MediaRecorder.start(Native Method)
Second, set the camera before setting the others like this.
recorder = new MediaRecorder();
recorder.setCamera( mCamera ); // like this!
recorder.setAudioSource( MediaRecorder.AudioSource.MIC);
recorder.setVideoSource( MediaRecorder.VideoSource.CAMERA);
recorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4);
recorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB);
recorder.setVideoEncoder(MediaRecorder.VideoEncoder.MPEG_4_SP);
recorder.setVideoSize( 2560, 1440 );
recorder.setVideoFrameRate(30);
recorder.setPreviewDisplay(holder.getSurface());
recorder.setOutputFile( s_dir );
try {
recorder.prepare();
recorder.start();
} catch( Exception e ) {
Log.e("SampleVideoRecorder", "Exception : ", e );
recorder.release();
recorder = null;
}
Someone says that setCamera() should be called before prepare().
But I'm watching my code is working.
Have you tried to use the following functions after creating an instance of mediarecorder?
//Unlocks the camera to allow another process to access it.
mCameraDevice.unlock();
//Sets a Camera to use for recording. Use this function to switch quickly between preview and //capture mode without a teardown of the camera object.
mMediaRecorder.setCamera(mCameraDevice);
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With