How to change preview of camera at runtime?

a 夏天 提交于 2020-06-08 14:21:51

问题


I am trying to create an app which captures some x*y sized rectangular portion from the camera view. To achieve that I have been to many threads but none of them seems to be working as required.

Basically what i want to achieve is as shown:

My requirement is when i open camera there should be a rectangular highlighted bright part on the screen and the rest of the screen should look black translucent displaying the rest of the camera view but when user clicks the button then the camera should only click the highlighted brighten part of the screen.

I am trying thisCustom camera android thread but it is not displaying the rest of the part as translucent. It only shows whatever comes under the surfaceview.

Now what i have done is using another surface view on top of it but now it is clicking the previous portion of the surface not the current one.

So please give me some advice to achieve the same.

My Activity code:

package com.example.cameraapplication;

import androidx.appcompat.app.AppCompatActivity;

import android.app.Activity;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.hardware.Camera;
import android.os.Bundle;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.Toast;

import java.io.IOException;

public class CameraActivity extends Activity implements Camera.PictureCallback, SurfaceHolder.Callback {

    public static final String EXTRA_CAMERA_DATA = "camera_data";

    private static final String KEY_IS_CAPTURING = "is_capturing";

    private Camera mCamera, dummyCamera;
    private ImageView mCameraImage;
    private SurfaceView mCameraPreview,s1;
    private Button mCaptureImageButton;
    private byte[] mCameraData;
    private boolean mIsCapturing;
    private View v1;

    private View.OnClickListener mCaptureImageButtonClickListener = new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            try {
                mCamera.stopPreview();
                mCamera.setPreviewDisplay(mCameraPreview.getHolder());
                mCamera.startPreview();
                captureImage();
            }catch (Exception e){
                e.printStackTrace();
            }
        }
    };

    private View.OnClickListener mRecaptureImageButtonClickListener = new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            setupImageCapture();
        }
    };

    private View.OnClickListener mDoneButtonClickListener = new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            if (mCameraData != null) {
                Intent intent = new Intent();
                intent.putExtra(EXTRA_CAMERA_DATA, mCameraData);
                setResult(RESULT_OK, intent);
            } else {
                setResult(RESULT_CANCELED);
            }
            finish();
        }
    };

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_camera);

        mCameraImage = (ImageView) findViewById(R.id.camera_image_view);
        mCameraImage.setVisibility(View.INVISIBLE);
        v1 = findViewById(R.id.v1);

        mCameraPreview = (SurfaceView) findViewById(R.id.preview_view);
        s1 = (SurfaceView) findViewById(R.id.preview_view_1);
        final SurfaceHolder surfaceHolder = mCameraPreview.getHolder();
        surfaceHolder.addCallback(this);
        surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);

        mCaptureImageButton = (Button) findViewById(R.id.capture_image_button);
        mCaptureImageButton.setOnClickListener(mCaptureImageButtonClickListener);

        final Button doneButton = (Button) findViewById(R.id.done_button);
        doneButton.setOnClickListener(mDoneButtonClickListener);

        mIsCapturing = true;
    }

    @Override
    protected void onSaveInstanceState(Bundle savedInstanceState) {
        super.onSaveInstanceState(savedInstanceState);

        savedInstanceState.putBoolean(KEY_IS_CAPTURING, mIsCapturing);
    }

    @Override
    protected void onRestoreInstanceState(Bundle savedInstanceState) {
        super.onRestoreInstanceState(savedInstanceState);

        mIsCapturing = savedInstanceState.getBoolean(KEY_IS_CAPTURING, mCameraData == null);
        if (mCameraData != null) {
            setupImageDisplay();
        } else {
            setupImageCapture();
        }
    }

    @Override
    protected void onResume() {
        super.onResume();

        if (mCamera == null) {
            try {
                mCamera = Camera.open();
//                dummyCamera = mCamera;
                mCamera.setPreviewDisplay(s1.getHolder());
//                dummyCamera.setPreviewDisplay(s1.getHolder());
                if (mIsCapturing) {
//                    dummyCamera.startPreview();
                    mCamera.startPreview();
                }
            } catch (Exception e) {
                e.printStackTrace();
                Toast.makeText(CameraActivity.this, "Unable to open camera.", Toast.LENGTH_LONG)
                        .show();
            }
        }
    }

    @Override
    protected void onPause() {
        super.onPause();

        if (mCamera != null) {
            mCamera.release();
            mCamera = null;
        }
    }

    @Override
    public void onPictureTaken(byte[] data, Camera camera) {
        mCameraData = data;
        setupImageDisplay();
    }

    @Override
    public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
        if (mCamera != null) {
            try {
                mCamera.setPreviewDisplay(mCameraPreview.getHolder());
//                dummyCamera.setPreviewDisplay(s1.getHolder());
                if (mIsCapturing) {
                    mCamera.startPreview();
//                    dummyCamera.startPreview();
                }
            } catch (IOException e) {
                e.printStackTrace();
                Toast.makeText(CameraActivity.this, "Unable to start camera preview.", Toast.LENGTH_LONG).show();
            }
        }
    }

    @Override
    public void surfaceCreated(SurfaceHolder holder) {
    }

    @Override
    public void surfaceDestroyed(SurfaceHolder holder) {
    }

    private void captureImage() {
        mCamera.takePicture(null, null, this);
    }

    private void setupImageCapture() {
        try {
            mCameraImage.setVisibility(View.INVISIBLE);
            mCameraPreview.setVisibility(View.VISIBLE);
            s1.setVisibility(View.VISIBLE);
            v1.setVisibility(View.VISIBLE);
            mCamera.setPreviewDisplay(s1.getHolder());
            mCamera.startPreview();
            mCaptureImageButton.setText(R.string.capture_image);
            mCaptureImageButton.setOnClickListener(mCaptureImageButtonClickListener);
        }catch (Exception e){
            e.printStackTrace();
        }
    }

    private void setupImageDisplay() {
        Bitmap bitmap = BitmapFactory.decodeByteArray(mCameraData, 0, mCameraData.length);
        mCameraImage.setImageBitmap(bitmap);
        mCamera.stopPreview();
        mCameraPreview.setVisibility(View.INVISIBLE);
        s1.setVisibility(View.INVISIBLE);
        v1.setVisibility(View.INVISIBLE);
        mCameraImage.setVisibility(View.VISIBLE);
        mCaptureImageButton.setText(R.string.recapture_image);
        mCaptureImageButton.setOnClickListener(mRecaptureImageButtonClickListener);
    }
}

Layout file:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:custom="http://schemas.android.com/apk/res-auto"
    android:background="@android:color/transparent"
    android:orientation="vertical">

    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@string/capturing_image" />

    <FrameLayout
        android:id="@+id/camera_frame"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1">

        <com.edmodo.cropper.CropImageView
            android:id="@+id/camera_image_view"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            />

        <!--        <ImageView-->
        <!--            android:id="@+id/camera_image_view"-->
        <!--            android:layout_width="match_parent"-->
        <!--            android:layout_height="match_parent" />-->

        <SurfaceView
            android:id="@+id/preview_view_1"
            android:layout_width="match_parent"
            android:layout_height="match_parent" />

        <View
            android:id="@+id/v1"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:background="#CCFFFFFF"/>

        <SurfaceView
            android:id="@+id/preview_view"
            android:layout_margin="80dp"
            android:layout_width="match_parent"
            android:layout_height="match_parent" />

<!--        <com.example.cameraapplication.CropOverlayNew-->
<!--            android:id="@+id/cropper"-->
<!--            android:layout_width="match_parent"-->
<!--            android:layout_height="match_parent"/>-->

        <!--        <LinearLayout-->
        <!--            android:layout_width="match_parent"-->
        <!--            android:background="@android:color/transparent"-->
        <!--            android:layout_height="match_parent">-->
        <!--            -->
        <!--        </LinearLayout>-->


    </FrameLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginTop="10dp"
        android:gravity="center"
        android:orientation="horizontal">

        <Button
            android:id="@+id/capture_image_button"
            android:layout_width="150dp"
            android:layout_height="wrap_content"
            android:text="@string/capture_image" />

        <Button
            android:id="@+id/done_button"
            android:layout_width="150dp"
            android:layout_height="wrap_content"
            android:text="@string/done" />
    </LinearLayout>

</LinearLayout>

来源:https://stackoverflow.com/questions/61728321/how-to-change-preview-of-camera-at-runtime

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!