注意,Camera API在API>=21已经被废弃了,建议使用android.hardware.camera2 API来进行操作。
调用Camera API拍照的流程如下:
To take pictures with this class, use the following steps:
open(int)
.getParameters()
.Camera.Parameters
object and call setParameters(Camera.Parameters)
.setDisplayOrientation(int)
.SurfaceHolder
to setPreviewDisplay(SurfaceHolder)
. Without a surface, the camera will be unable to start the preview.startPreview()
to start updating the preview surface. Preview must be started before you can take a picture.takePicture(Camera.ShutterCallback, Camera.PictureCallback, Camera.PictureCallback, Camera.PictureCallback)
to capture a photo. Wait for the callbacks to provide the actual image data.startPreview()
again first.stopPreview()
to stop updating the preview surface.release()
to release the camera for use by other applications. Applications should release the camera immediately in onPause()
(and re-open()
it in onResume()
).1、声明所需权限
<uses-permission android:name="android.permission.CAMERA" />
<uses-feature android:name="android.hardware.camera" />
<uses-feature android:name="android.hardware.camera.autofocus" />
2、通过Camera.open()获取Camera实例,对于多个摄像头,那么需要遍历getNumberOfCameras(),获取每一个CameraInfo来判断是前置摄像头还是后置摄像头。
Camera.CameraInfo info = new Camera.CameraInfo();
Camera.getCameraInfo(cameraId, info);
if (info.facing == Camera.CameraInfo.CAMERA_FACING_FRONT) {//前置摄像头
} else { // 后置摄像头
}
3、Camera.Parameters类是对Camera的设置操作,包括闪光灯、自动对焦,场景,白平衡等,有需要可以设置。
PS:闪光灯就是setFlashMode(Camera.Parameters.FLASH_MODE_TORCH)来实现的
4、设置Camera的方向,官方提供的算法如下:
public static void setCameraDisplayOrientation(Activity activity,
int cameraId, android.hardware.Camera camera) {
android.hardware.Camera.CameraInfo info =
new android.hardware.Camera.CameraInfo();
android.hardware.Camera.getCameraInfo(cameraId, info);
int rotation = activity.getWindowManager().getDefaultDisplay()
.getRotation();
int degrees = 0;
switch (rotation) {
case Surface.ROTATION_0: degrees = 0; break;
case Surface.ROTATION_90: degrees = 90; break;
case Surface.ROTATION_180: degrees = 180; break;
case Surface.ROTATION_270: degrees = 270; break;
}
int result;
if (info.facing == Camera.CameraInfo.CAMERA_FACING_FRONT) {
result = (info.orientation + degrees) % 360;
result = (360 - result) % 360; // compensate the mirror
} else { // back-facing
result = (info.orientation - degrees + 360) % 360;
}
camera.setDisplayOrientation(result);
}
5、设置预览视图(SurfaceHolder),一般在xml里面自定义SurfaceView,然后在Activity或者Fragment里面初始化
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_photo, container, false);
SurfaceView surfaceView = (SurfaceView) rootView.findViewById(R.id.surface);
surfaceView.getHolder().addCallback(this);
//此方法在API<11的手机上必须调用,否则没有效果
surfaceView.getHolder().setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
return rootView;
}
6、启动预览和Camera声明周期管理
@Override
public void surfaceCreated(SurfaceHolder holder) {
mCamera = Camera.open();
try {
mCamera.setPreviewDisplay(holder);
} catch (Exception e) {
e.printStackTrace();
return ;
}
setCameraDisplayOrientation(getActivity(), Camera.getNumberOfCameras()-1,mCamera);
mCamera.startPreview();
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
}
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
mCamera.stopPreview();
mCamera.release();
}
7、拍照直接调用Camera.takePicture()即可。
原文:http://www.cnblogs.com/alexthecoder/p/4363516.html