当我的应用相机在Android中启动时,如何连续将图像保存到缓冲区?

时间:2016-12-18 14:26:07

标签: android camera

在我的应用程序中,我想在用户尝试捕获图像之前,一旦用户启动相机捕获相机的帧,就将图像保存到缓冲区。请建议我在android中实现这一点的具体方法。

1 个答案:

答案 0 :(得分:0)

在旧相机api中,您可以相对轻松地访问预览帧数据。 从Android 5.0开始引入camera2,设置正确的处理程序和状态要复杂得多。

现在发布Android 7.0的主要问题是:您是否可以使用旧的,已弃用的代码?由于我们的一些Android手机仍然使用4.2和4.4其他5.0a和6.0对我来说很好,但我不知道你的情况。

这里我刚刚删除了一个自定义颜色,比如如何移除绿色屏幕,但是如果用户触摸预览屏幕,它将选择所需的颜色,如棕色或蓝色等。

private class CameraPreviewCallback implements Camera.PreviewCallback {

    private int curColor, curRed, curGreen, curBlue;

    @Override
    public void onPreviewFrame(byte[] data, Camera camera) {

        // conversion:
        decodeYUV420SP(mRgb, data, mSurfWidth, mSurfHeight);

        // check if need an update for the selected color
        if (mRequestColorUpdate) {
            int arrayIndex = mTouchY * mSurfWidth + mTouchX;
            mChoosedColor = mRgb[arrayIndex];
            btRecordVideo.setBackgroundColor(mChoosedColor);
            mRequestColorUpdate = false;
            updateBackgroundRemovalLimits();

           // do my stuff, not important here
        }
        // remove background:
        for (int i = 0; i < mRgb.length; i++) {
            curColor = mRgb[i];
            // split:
            curRed = Color.red(curColor);
            curGreen = Color.green(curColor);
            curBlue = Color.blue(curColor);

            if ((minRed <= curRed) && (curRed <= maxRed) && (minGreen <= curGreen) && (curGreen <= maxGreen) && (minBlue <= curBlue) && (curBlue <= maxBlue)) {
                // set alpha to 0 bitwise:
                mRgb[i] = curColor & 0x00FFFFFF;
            }
        }

        // update the modified preview screen:
        mBitmap.setPixels(mRgb, 0, mSurfWidth, 0, 0, mSurfWidth, mSurfHeight);
        if (ivPreviewModified != null) {
            ivPreviewModified.setImageBitmap(mBitmap);
        }
    }
}

您必须添加到相机:

 camera.setPreviewCallback(new CameraPreviewCallback());

相机初始化如下:

@Override
public void onResume() {
    super.onResume();
    //
    camera = Camera.open();
    startPreview();
}

这是来自stackoverflow:)

public class YuvToRgb {

    //  Byte decoder : ---------------------------------------------------------------------
   public static final void decodeYUV420SP(int[] rgb, byte[] yuv420sp, int width, int height) {
        // Pulled directly from:
        // http://ketai.googlecode.com/svn/trunk/ketai/src/edu/uic/ketai/inputService/KetaiCamera.java
        final int frameSize = width * height;

        for (int j = 0, yp = 0; j < height; j++) {
            int uvp = frameSize + (j >> 1) * width, u = 0, v = 0;
            for (int i = 0; i < width; i++, yp++) {
                int y = (0xff & ((int) yuv420sp[yp])) - 16;
                if (y < 0)
                    y = 0;
                if ((i & 1) == 0) {
                    v = (0xff & yuv420sp[uvp++]) - 128;
                    u = (0xff & yuv420sp[uvp++]) - 128;
                }

                int y1192 = 1192 * y;
                int r = (y1192 + 1634 * v);
                int g = (y1192 - 833 * v - 400 * u);
                int b = (y1192 + 2066 * u);

                if (r < 0)
                    r = 0;
                else if (r > 262143)
                    r = 262143;
                if (g < 0)
                    g = 0;
                else if (g > 262143)
                    g = 262143;
                if (b < 0)
                    b = 0;
                else if (b > 262143)
                    b = 262143;

                rgb[yp] = 0xff000000 | ((r << 6) & 0xff0000) | ((g >> 2) & 0xff00) | ((b >> 10) & 0xff);
            }
        }
    }
}