Android 使用Camera2 打开预览Demo

camera.xml

<?xml version="1.0" encoding="utf-8"?>        

Camera2Test.java

package com.neostra.closereminder;import android.annotation.SuppressLint;import android.app.Activity;import android.content.Context;import android.graphics.*;import android.hardware.camera2.*;import android.hardware.camera2.params.StreamConfigurationMap;import android.os.Bundle;import android.os.Handler;import android.os.HandlerThread;import android.support.annotation.Nullable;import android.util.Log;import android.util.Size;import android.view.Surface;import android.view.TextureView;import android.view.View;import java.util.*;public class Camera2Test extends Activity {    private static final String TAG = "Camera2Test";    private String mCameraId;    private Size mPreviewSize;    private TextureView mTextureView;    private CameraDevice mCameraDevice;    private CameraManager mCameraManager;    private CaptureRequest mPreviewRequest;    private CameraCaptureSession mCaptureSession;    private Handler mBackgroundHandler;    private HandlerThread mBackgroundThread;    private final CameraDevice.StateCallback mStateCallback = new CameraDevice.StateCallback() {        @Override        public void onOpened(CameraDevice cameraDevice) {            mCameraDevice = cameraDevice;            createCameraPreviewSession();        }        @Override        public void onDisconnected(CameraDevice cameraDevice) {            cameraDevice.close();            mCameraDevice = null;        }        @Override        public void onError(CameraDevice cameraDevice, int error) {            cameraDevice.close();            mCameraDevice = null;        }    };    private final TextureView.SurfaceTextureListener mSurfaceTextureListener = new TextureView.SurfaceTextureListener() {        @Override        public void onSurfaceTextureAvailable(SurfaceTexture texture, int width, int height) {            openCamera(width, height);        }        @Override        public void onSurfaceTextureSizeChanged(SurfaceTexture texture, int width, int height) {            configureTransform(width, height);        }        @Override        public boolean onSurfaceTextureDestroyed(SurfaceTexture texture) {            return true;        }        @Override        public void onSurfaceTextureUpdated(SurfaceTexture texture) {            // NOOP        }    };    @Override    protected void onCreate(@Nullable Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        mCameraManager = (CameraManager) getSystemService(Context.CAMERA_SERVICE);        setContentView(R.layout.camera);        mTextureView = findViewById(R.id.textureView);        findViewById(R.id.btnStart).setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View v) {                try {                    mCaptureSession.setRepeatingRequest(mPreviewRequest, null, mBackgroundHandler);                } catch (CameraAccessException e) {                    e.printStackTrace();                }            }        });        findViewById(R.id.btnStop).setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View v) {                try {                    mCaptureSession.stopRepeating();                } catch (CameraAccessException e) {                    e.printStackTrace();                }            }        });    }    @Override    protected void onStart() {        super.onStart();        startBackgroundThread();        if (mTextureView.isAvailable()) {            openCamera(mTextureView.getWidth(), mTextureView.getHeight());        } else {            mTextureView.setSurfaceTextureListener(mSurfaceTextureListener);        }    }    @Override    protected void onStop() {        closeCamera();        stopBackgroundThread();        super.onStop();    }    @SuppressLint("MissingPermission")    private void openCamera(int width, int height) {        setUpCameraOutputs(width, height);        configureTransform(width, height);        try {            mCameraManager.openCamera(mCameraId, mStateCallback, mBackgroundHandler);        } catch (Exception e) {            e.printStackTrace();        }    }    private void closeCamera() {        if (mCaptureSession != null) {            mCaptureSession.close();            mCaptureSession = null;        }        if (mCameraDevice != null) {            mCameraDevice.close();            mCameraDevice = null;        }    }    private void startBackgroundThread() {        mBackgroundThread = new HandlerThread("CameraBackground");        mBackgroundThread.start();        mBackgroundHandler = new Handler(mBackgroundThread.getLooper());    }    private void stopBackgroundThread() {        mBackgroundThread.quitSafely();        try {            mBackgroundThread.join();            mBackgroundThread = null;            mBackgroundHandler = null;        } catch (InterruptedException e) {            e.printStackTrace();        }    }    private void createCameraPreviewSession() {        try {            SurfaceTexture texture = mTextureView.getSurfaceTexture();            texture.setDefaultBufferSize(mPreviewSize.getWidth(), mPreviewSize.getHeight());            Surface surface = new Surface(texture);            final CaptureRequest.Builder previewRequestBuilder = mCameraDevice.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);            previewRequestBuilder.addTarget(surface);            mCameraDevice.createCaptureSession(Arrays.asList(surface), new CameraCaptureSession.StateCallback() {                @Override                public void onConfigured(CameraCaptureSession cameraCaptureSession) {                    mCaptureSession = cameraCaptureSession;                    try {                        previewRequestBuilder.set(CaptureRequest.CONTROL_AF_MODE, CaptureRequest.CONTROL_AF_MODE_CONTINUOUS_PICTURE);                        mPreviewRequest = previewRequestBuilder.build();                        mCaptureSession.setRepeatingRequest(mPreviewRequest, null, mBackgroundHandler);                    } catch (CameraAccessException e) {                        e.printStackTrace();                    }                }                @Override                public void onConfigureFailed(CameraCaptureSession cameraCaptureSession) {                    Log.e(TAG, "onConfigureFailed");                }            }, null);        } catch (CameraAccessException e) {            e.printStackTrace();        }    }    // ======================================== 工具方法 ========================================    private void setUpCameraOutputs(int width, int height) {        try {            for (String cameraId : mCameraManager.getCameraIdList()) {                CameraCharacteristics characteristics = mCameraManager.getCameraCharacteristics(cameraId);                StreamConfigurationMap map = characteristics.get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP);                if (map == null) {                    continue;                }                Size largest = Collections.max(Arrays.asList(map.getOutputSizes(ImageFormat.JPEG)), new CompareSizesByArea());                Point displaySize = new Point();                getWindowManager().getDefaultDisplay().getSize(displaySize);                int maxPreviewWidth = displaySize.x;                int maxPreviewHeight = displaySize.y;                mPreviewSize = chooseOptimalSize(map.getOutputSizes(SurfaceTexture.class), width, height, maxPreviewWidth, maxPreviewHeight, largest);                mCameraId = cameraId;                return;            }        } catch (Exception e) {            e.printStackTrace();        }    }    private void configureTransform(int viewWidth, int viewHeight) {        int rotation = getWindowManager().getDefaultDisplay().getRotation();        Matrix matrix = new Matrix();        RectF viewRect = new RectF(0, 0, viewWidth, viewHeight);        float centerX = viewRect.centerX();        float centerY = viewRect.centerY();        /*if (Surface.ROTATION_90 == rotation || Surface.ROTATION_270 == rotation) {            RectF bufferRect = new RectF(0, 0, mPreviewSize.getHeight(), mPreviewSize.getWidth());            bufferRect.offset(centerX - bufferRect.centerX(), centerY - bufferRect.centerY());            matrix.setRectToRect(viewRect, bufferRect, Matrix.ScaleToFit.FILL);            float scale = Math.max((float) viewHeight / mPreviewSize.getHeight(), (float) viewWidth / mPreviewSize.getWidth());            matrix.postScale(scale, scale, centerX, centerY);            matrix.postRotate(90 * (rotation - 2), centerX, centerY);        } else if (Surface.ROTATION_180 == rotation) {            matrix.postRotate(180, centerX, centerY);        }*/        mTextureView.setTransform(matrix);    }    private static Size chooseOptimalSize(Size[] choices, int textureViewWidth, int textureViewHeight, int maxWidth, int maxHeight, Size aspectRatio) {        List bigEnough = new ArrayList<>();        List notBigEnough = new ArrayList<>();        int w = aspectRatio.getWidth();        int h = aspectRatio.getHeight();        for (Size option : choices) {            if (option.getWidth() <= maxWidth && option.getHeight() <= maxHeight && option.getHeight() == option.getWidth() * h / w) {                if (option.getWidth() >= textureViewWidth && option.getHeight() >= textureViewHeight) {                    bigEnough.add(option);                } else {                    notBigEnough.add(option);                }            }        }        if (bigEnough.size() > 0) {            return Collections.min(bigEnough, new CompareSizesByArea());        } else if (notBigEnough.size() > 0) {            return Collections.max(notBigEnough, new CompareSizesByArea());        } else {            Log.e(TAG, "Couldn't find any suitable preview size");            return choices[0];        }    }    private static class CompareSizesByArea implements Comparator {        @Override        public int compare(Size lhs, Size rhs) {            return Long.signum((long) lhs.getWidth() * lhs.getHeight() - (long) rhs.getWidth() * rhs.getHeight());        }    }}

添加Camera权限
AndroidManifest.xml

         
发表评论
留言与评论(共有 0 条评论) “”
   
验证码:

相关文章

推荐文章