FileDocCategorySizeDatePackage
CameraPreviewActivity.javaAPI DocAndroid 5.1 API11898Thu Mar 12 22:22:54 GMT 2015com.android.rs.livepreview

CameraPreviewActivity

public class CameraPreviewActivity extends android.app.Activity implements Camera.PreviewCallback, TextureView.SurfaceTextureListener
Tests for manual verification of the CDD-required camera output formats for preview callbacks

Fields Summary
private static final String
TAG
private android.view.TextureView
mPreviewView
private android.graphics.SurfaceTexture
mPreviewTexture
private int
mPreviewTexWidth
private int
mPreviewTexHeight
private android.widget.Spinner
mCameraSpinner
private android.widget.Spinner
mResolutionSpinner
private int
mCurrentCameraId
private android.hardware.Camera
mCamera
private List
mPreviewSizes
private Camera.Size
mNextPreviewSize
private Camera.Size
mPreviewSize
private android.view.TextureView
mOutputView
private static final int
STATE_OFF
private static final int
STATE_PREVIEW
private static final int
STATE_NO_CALLBACKS
private int
mState
private boolean
mProcessInProgress
private boolean
mProcessingFirstFrame
private RenderScript
mRS
private RsYuv
mFilterYuv
private AdapterView.OnItemSelectedListener
mCameraSpinnerListener
private AdapterView.OnItemSelectedListener
mResolutionSelectedListener
private long[]
mTiming
private int
mTimingSlot
Constructors Summary
Methods Summary
public voidonCreate(android.os.Bundle savedInstanceState)


    
        
        super.onCreate(savedInstanceState);

        setContentView(R.layout.cf_main);

        mPreviewView = (TextureView) findViewById(R.id.preview_view);
        mOutputView = (TextureView) findViewById(R.id.format_view);

        mPreviewView.setSurfaceTextureListener(this);

        int numCameras = Camera.getNumberOfCameras();
        String[] cameraNames = new String[numCameras];
        for (int i = 0; i < numCameras; i++) {
            cameraNames[i] = "Camera " + i;
        }
        mCameraSpinner = (Spinner) findViewById(R.id.cameras_selection);
        mCameraSpinner.setAdapter(
            new ArrayAdapter<String>(
                this, R.layout.cf_format_list_item, cameraNames));
        mCameraSpinner.setOnItemSelectedListener(mCameraSpinnerListener);

        mResolutionSpinner = (Spinner) findViewById(R.id.resolution_selection);
        mResolutionSpinner.setOnItemSelectedListener(mResolutionSelectedListener);

        mRS = RenderScript.create(this);
        mFilterYuv = new RsYuv(mRS);
        mOutputView.setSurfaceTextureListener(mFilterYuv);
    
public voidonPause()

        super.onPause();

        shutdownCamera();
    
public voidonPreviewFrame(byte[] data, android.hardware.Camera camera)


          
        if (mProcessInProgress || mState != STATE_PREVIEW) {
            mCamera.addCallbackBuffer(data);
            return;
        }
        if (data == null) {
            return;
        }

        int expectedBytes = mPreviewSize.width * mPreviewSize.height *
                ImageFormat.getBitsPerPixel(ImageFormat.NV21) / 8;

        if (expectedBytes != data.length) {
            Log.e(TAG, "Mismatched size of buffer! Expected ");

            mState = STATE_NO_CALLBACKS;
            mCamera.setPreviewCallbackWithBuffer(null);
            return;
        }

        mProcessInProgress = true;

        if ((mFilterYuv == null) ||
            (mPreviewSize.width != mFilterYuv.getWidth()) ||
            (mPreviewSize.height != mFilterYuv.getHeight()) ) {

            mFilterYuv.reset(mPreviewSize.width, mPreviewSize.height);
        }

        mProcessInProgress = true;
        new ProcessPreviewDataTask().execute(data);
    
public voidonResume()

        super.onResume();

        setUpCamera(mCameraSpinner.getSelectedItemPosition());
    
public voidonSurfaceTextureAvailable(android.graphics.SurfaceTexture surface, int width, int height)

        mPreviewTexture = surface;
        mPreviewTexWidth = width;
        mPreviewTexHeight = height;
        if (mCamera != null) {
            startPreview();
        }
    
public booleanonSurfaceTextureDestroyed(android.graphics.SurfaceTexture surface)

        return true;
    
public voidonSurfaceTextureSizeChanged(android.graphics.SurfaceTexture surface, int width, int height)

        // Ignored, Camera does all the work for us
    
public voidonSurfaceTextureUpdated(android.graphics.SurfaceTexture surface)

        // Invoked every time there's a new Camera preview frame
    
private voidsetUpCamera(int id)



        
        shutdownCamera();

        mCurrentCameraId = id;
        mCamera = Camera.open(id);
        Camera.Parameters p = mCamera.getParameters();

        // Get preview resolutions

        List<Camera.Size> unsortedSizes = p.getSupportedPreviewSizes();

        class SizeCompare implements Comparator<Camera.Size> {
            public int compare(Camera.Size lhs, Camera.Size rhs) {
                if (lhs.width < rhs.width) return -1;
                if (lhs.width > rhs.width) return 1;
                if (lhs.height < rhs.height) return -1;
                if (lhs.height > rhs.height) return 1;
                return 0;
            }
        };

        SizeCompare s = new SizeCompare();
        TreeSet<Camera.Size> sortedResolutions = new TreeSet<Camera.Size>(s);
        sortedResolutions.addAll(unsortedSizes);

        mPreviewSizes = new ArrayList<Camera.Size>(sortedResolutions);

        String[] availableSizeNames = new String[mPreviewSizes.size()];
        for (int i = 0; i < mPreviewSizes.size(); i++) {
            availableSizeNames[i] =
                    Integer.toString(mPreviewSizes.get(i).width) + " x " +
                    Integer.toString(mPreviewSizes.get(i).height);
        }
        mResolutionSpinner.setAdapter(
            new ArrayAdapter<String>(
                this, R.layout.cf_format_list_item, availableSizeNames));


        // Set initial values
	//
        int initialSize = mPreviewSizes.size() - 1;

	mNextPreviewSize = mPreviewSizes.get(initialSize);
        mResolutionSpinner.setSelection(initialSize);

	if(mPreviewTexture != null)
	{
            startPreview();
        }
    
private voidshutdownCamera()

        if (mCamera != null) {
            mCamera.setPreviewCallbackWithBuffer(null);
            mCamera.stopPreview();
            mCamera.release();
            mCamera = null;
            mState = STATE_OFF;
        }
    
private voidstartPreview()

        if (mState != STATE_OFF) {
            // Stop for a while to drain callbacks
            mCamera.setPreviewCallbackWithBuffer(null);
            mCamera.stopPreview();
            mState = STATE_OFF;
            Handler h = new Handler();
            Runnable mDelayedPreview = new Runnable() {
                public void run() {
                    startPreview();
                }
            };
            h.postDelayed(mDelayedPreview, 300);
            return;
        }
        mState = STATE_PREVIEW;

        Matrix transform = new Matrix();
        float widthRatio = mNextPreviewSize.width / (float)mPreviewTexWidth;
        float heightRatio = mNextPreviewSize.height / (float)mPreviewTexHeight;

        transform.setScale(1, heightRatio/widthRatio);
        transform.postTranslate(0,
                mPreviewTexHeight * (1 - heightRatio/widthRatio)/2);

        mPreviewView.setTransform(transform);
        mOutputView.setTransform(transform);

        mPreviewSize   = mNextPreviewSize;

        Camera.Parameters p = mCamera.getParameters();
        p.setPreviewFormat(ImageFormat.NV21);
        p.setPreviewSize(mPreviewSize.width, mPreviewSize.height);
        mCamera.setParameters(p);

        mCamera.setPreviewCallbackWithBuffer(this);
        int expectedBytes = mPreviewSize.width * mPreviewSize.height *
                ImageFormat.getBitsPerPixel(ImageFormat.NV21) / 8;
        for (int i=0; i < 4; i++) {
            mCamera.addCallbackBuffer(new byte[expectedBytes]);
        }
        //mFormatView.setColorFilter(mYuv2RgbFilter);

        mProcessingFirstFrame = true;
        try {
            mCamera.setPreviewTexture(mPreviewTexture);
            mCamera.startPreview();
        } catch (IOException ioe) {
            // Something bad happened
            Log.e(TAG, "Unable to start up preview");
        }