Android的前置摄像头拍摄照片倒置摄像头、照片、Android

2023-09-06 08:44:25 作者:抱小熊

我有这样的应用程序,在纵向模式,并作为一个活动的一部分运行我有一个摄像头对象中运行在它的片段。

我要从前到后置摄像头切换选项,并用相机背面拍照时,一切都很好很好。

当我拍照的前置摄像头,虽然,他们得到反转180度。 现在我知道,这可能是与纵向模式的方向是,但有它的景观会杀了我的应用程序的想法。

有反正这是可以固定的,所以拍摄的画面是一样的一个你在preVIEW看?

 监听器=新OrientationEventListener(this.getActivity(),SensorManager.SENSOR_DELAY_NORMAL){

        @覆盖
        公共无效onOrientationChanged(INT方向){
            // TODO自动生成方法存根
            如果(定向== ORIENTATION_UNKNOWN)回报;
             android.hardware.Camera.CameraInfo信息=
                    新android.hardware.Camera.CameraInfo();
             android.hardware.Camera.getCameraInfo(mCurrentCamera,资讯);
             定向=(方向+ 45)/ 90 * 90;
             INT旋转= 0;
             如果(info.facing == CameraInfo.CAMERA_FACING_FRONT){
                 旋转=(info.orientation  - 方向+ 360)%360;
             }其他{//背置摄像头
                 旋转=(info.orientation +方向)360%;
             }
             如果(mCamera.getParameters()!= NULL){
             Camera.Parameters mParameters = mCamera.getParameters();

             mParameters.setRotation(旋转);
             mCamera.setParameters(mParameters);
             }
        }

    };
    listener.enable();
    如果(listener.canDetectOrientation())
        Log.d(方向的可能,方向可能);
 

现在的问题是,当我尝试使用拍照这件事崩溃。此外,如果它运行的只是preVIEW模式,而它再次崩溃。我还要也许应该补充,在另一种方法,我这样做。

 公共无效switchCamera(摄像机镜头){
    setCamera(照相机);
    尝试 {
        camera.set previewDisplay(mHolder);
    }赶上(IOException异常除外){
        Log.e(TAG,IOException异常造成集previewDisplay(),除外);
    }
    Camera.Parameters参数= camera.getParameters();
    parameters.set previewSize(M previewSize.width,男previewSize.height);

    requestLayout();


    尝试{
        camera.setParameters(参数);
    }
    赶上(RuntimeException的前){
        Log.d(preVIEW,未设置合适的参数);
        //需要改进此方法
        如果(mSupported previewSizes!= NULL){
            Camera.Size CS = mSupported previewSizes.get(0);
            parameters.set previewSize(cs.width,cs.height);
            camera.setParameters(参数);
            requestLayout();
            // INT tempheight = M previewSize.height;
            //m$p$pviewSize.height = M previewSize.width;
            //m$p$pviewSize.width = tempheight;

        }
    }
 
云 时代通信变革 移动互联多媒体

在摄像头之间切换(回面对前置反之亦然),这就是所谓的。难道这是与定向事件侦听器的干扰?

此外,节省拍摄照片的时候,这就是我所说的。之前,它刚刚以数据作为参数,但我试图使它采取屏幕的方向为好。问题是屏幕的方向始终是90,不管是什么。因此,位图总是90度(这是伟大的拍照与相机背面),但与前相机拍摄时,它反转旋转。可在此功能的修复来实现?

 公共静态位图MakeSquare(byte []的数据,INT方向){
    INT宽度;
    INT高度;
    //旋转照片
    字模=新的Matrix();
    matrix.postRotate(方向);
    //转换ByteArray的位图
    位图bitPic = BitmapFactory.de codeByteArray(数据,0,data.length);
    宽度= bitPic.getWidth();
    身高= bitPic.getHeight();


    //创建新位图走出旧
    位图bitPicFinal = Bitmap.createBitmap(bitPic,0,0,宽度,高度,矩阵,真);
    bitPic.recycle();
    INT desWidth;
    INT desHeight;
    desWidth = bitPicFinal.getWidth();
    desHeight = desWidth;
    位图croppedBitmap = Bitmap.createBitmap(bitPicFinal,0,bitPicFinal.getHeight()/ 2  -  bitPicFinal.getWidth()/ 2,desWidth,desHeight);
    croppedBitmap = Bitmap.createScaledBitmap(croppedBitmap,528,528,真正的);
    返回croppedBitmap;
}
 

解决方案

好吧好吧。似乎有种我已经采取了照顾它。我用的这个建议:Android,正面和背面摄像头方向,横向

和改变了我的MakeSquare功能如下:

 公共静态位图MakeSquare(byte []的数据,诠释cameraID){
    INT宽度;
    INT高度;
    字模=新的Matrix();
    Camera.CameraInfo信息=新Camera.CameraInfo();
    android.hardware.Camera.getCameraInfo(cameraID,资讯);
    //转换ByteArray的位图
    位图bitPic = BitmapFactory.de codeByteArray(数据,0,data.length);
    宽度= bitPic.getWidth();
    身高= bitPic.getHeight();

    //进行矩阵转/后视镜视摄像头,拍下这张照片
    如果(info.facing == Camera.CameraInfo.CAMERA_FACING_FRONT)
    {
        浮[] mirrorY = {-1,0,0,0,1,0,0,0,1};
        矩阵matrixMirrorY =新的Matrix();
        matrixMirrorY.setValues​​(mirrorY);

        matrix.postConcat(matrixMirrorY);
    }

    matrix.postRotate(90);


    //创建新位图走出旧
    位图bitPicFinal = Bitmap.createBitmap(bitPic,0,0,宽度,高度,矩阵,真);
    bitPic.recycle();
    INT desWidth;
    INT desHeight;
    desWidth = bitPicFinal.getWidth();
    desHeight = desWidth;
    位图croppedBitmap = Bitmap.createBitmap(bitPicFinal,0,bitPicFinal.getHeight()/ 2  -  bitPicFinal.getWidth()/ 2,desWidth,desHeight);
    croppedBitmap = Bitmap.createScaledBitmap(croppedBitmap,528,528,真正的);
    返回croppedBitmap;
}
 

这似乎工作和做的伎俩。虽然我不知道这是最好的方法,我知足吧。现在我要做的就是找​​出为什么它使用前置摄像头时,没有采取在适当的纵横比。

I have this app that is running in portrait mode and as a part of one activity I have a camera object running as a fragment in it.

I have the option to switch from front to back-facing camera and when taking photos with the back camera all is fine and well.

When I take photos with the front-facing camera though, they get inverted 180 degrees. Now I know that this is probably something to do with the orientation being in portrait mode, but having it in landscape would just kill the idea of my application.

Is there anyway this can be fixed so the picture taken is the same as the one you see in the preview?

        listener = new OrientationEventListener(this.getActivity(),SensorManager.SENSOR_DELAY_NORMAL){

        @Override
        public void onOrientationChanged(int orientation) {
            // TODO Auto-generated method stub
            if (orientation == ORIENTATION_UNKNOWN) return;
             android.hardware.Camera.CameraInfo info =
                    new android.hardware.Camera.CameraInfo();
             android.hardware.Camera.getCameraInfo(mCurrentCamera, info);
             orientation = (orientation + 45) / 90 * 90;
             int rotation = 0;
             if (info.facing == CameraInfo.CAMERA_FACING_FRONT) {
                 rotation = (info.orientation - orientation + 360) % 360;
             } else {  // back-facing camera
                 rotation = (info.orientation + orientation) % 360;
             }
             if (mCamera.getParameters() != null){
             Camera.Parameters mParameters = mCamera.getParameters();

             mParameters.setRotation(rotation);
             mCamera.setParameters(mParameters);
             }
        }

    };
    listener.enable();
    if (listener.canDetectOrientation())
        Log.d("Orientation Possible", "Orientation Possible");

The problem is, after I try an take a picture this thing crashes. Also, if it runs for a while just in preview mode it crashes again. I also should probably add, that in another method I am doing this.

   public void switchCamera(Camera camera) {
    setCamera(camera);
    try {
        camera.setPreviewDisplay(mHolder);
    } catch (IOException exception) {
        Log.e(TAG, "IOException caused by setPreviewDisplay()", exception);
    }
    Camera.Parameters parameters = camera.getParameters();
    parameters.setPreviewSize(mPreviewSize.width, mPreviewSize.height);

    requestLayout();


    try{
        camera.setParameters(parameters);
    }
    catch (RuntimeException ex){
        Log.d("Preview", "Failure to set proper parameters");
        //need to improve this method
        if (mSupportedPreviewSizes != null) {
            Camera.Size cs = mSupportedPreviewSizes.get(0);
            parameters.setPreviewSize(cs.width, cs.height);
            camera.setParameters(parameters);
            requestLayout();
            //int tempheight = mPreviewSize.height;
            //mPreviewSize.height = mPreviewSize.width;
            //mPreviewSize.width = tempheight;

        }
    }

This is called when you switch between cameras(back facing to front facing vice-versa). Could this be interfering with the orientation event listener?

Also, when saving the picture taken, this is what I call. Before it was just taking in data as a parameter, but I tried to make it take screen orientation as well. The problem is the screen orientation is always 90, no matter what. So the bitmap will always be rotated by 90 degrees(which is great for taking photos with the back camera) but inverts it when taking it with the front camera. Could a fix be implemented in this function?

  public static Bitmap MakeSquare(byte[] data, int orientation) {
    int width;
    int height;
    // Rotate photo
    Matrix matrix = new Matrix();
    matrix.postRotate(orientation);
    // Convert ByteArray to Bitmap
    Bitmap bitPic = BitmapFactory.decodeByteArray(data, 0, data.length);
    width = bitPic.getWidth();
    height = bitPic.getHeight();


    // Create new Bitmap out of the old one
    Bitmap bitPicFinal = Bitmap.createBitmap(bitPic, 0, 0, width, height,matrix, true);
    bitPic.recycle();
    int desWidth;
    int desHeight;
    desWidth = bitPicFinal.getWidth();
    desHeight = desWidth;
    Bitmap croppedBitmap = Bitmap.createBitmap(bitPicFinal, 0,bitPicFinal.getHeight() / 2 - bitPicFinal.getWidth() / 2,desWidth, desHeight);
    croppedBitmap = Bitmap.createScaledBitmap(croppedBitmap, 528, 528, true);
    return croppedBitmap;
}

解决方案

Well well. It seems I have kind of taken care of it. I used the advice from this: Android, front and back camera Orientation , Landscape

And changed my MakeSquare function to this:

public static Bitmap MakeSquare(byte[] data, int cameraID) {
    int width;
    int height;
    Matrix matrix = new Matrix();
    Camera.CameraInfo info = new Camera.CameraInfo();
    android.hardware.Camera.getCameraInfo(cameraID, info);
    // Convert ByteArray to Bitmap
    Bitmap bitPic = BitmapFactory.decodeByteArray(data, 0, data.length);
    width = bitPic.getWidth();
    height = bitPic.getHeight();

    // Perform matrix rotations/mirrors depending on camera that took the photo
    if (info.facing == Camera.CameraInfo.CAMERA_FACING_FRONT)
    {
        float[] mirrorY = { -1, 0, 0, 0, 1, 0, 0, 0, 1};
        Matrix matrixMirrorY = new Matrix();
        matrixMirrorY.setValues(mirrorY);

        matrix.postConcat(matrixMirrorY);
    }

    matrix.postRotate(90);


    // Create new Bitmap out of the old one
    Bitmap bitPicFinal = Bitmap.createBitmap(bitPic, 0, 0, width, height,matrix, true);
    bitPic.recycle();
    int desWidth;
    int desHeight;
    desWidth = bitPicFinal.getWidth();
    desHeight = desWidth;
    Bitmap croppedBitmap = Bitmap.createBitmap(bitPicFinal, 0,bitPicFinal.getHeight() / 2 - bitPicFinal.getWidth() / 2,desWidth, desHeight);
    croppedBitmap = Bitmap.createScaledBitmap(croppedBitmap, 528, 528, true);
    return croppedBitmap;
}

This seems to work and do the trick. Although I am not sure this was the best way, I am content with it. Now all I have to do is figure out why its not taking in the proper aspect ratio when using the front camera.