美文网首页
Android摄像头相关问题解决

Android摄像头相关问题解决

作者: 修塔寻千里 | 来源:发表于2018-05-16 15:15 被阅读0次

    前置摄像头预览倒置问题解决

    近期做拍照和视频录制功能,发现谷歌Nexus系列手机在使用前置摄像头时,预览会出现图像倒置的问题,网上Google 了一下,查到官方回应:

    Because of manufacturing reasons, we needed to mount the Nexus 5X main sensor in the less-common (reverse landscape) orientation - the wires from the sensor chip wouldn't have fit otherwise. Unfortunately, our old camera API (which is deprecated, but most apps still use it) isn't terribly user-friendly, and requires application developers to explicitly set the preview rotation. On most devices, though, it turns out the default rotation is correct for a forced-landscape app, so many apps never call the display orientation method.

    问题所在:前置摄像头因为硬件原因是到着装的,采用正常手机适配会存在角度偏转问题。好在谷歌提供了解决方案:

    So if you do see apps with upside-down camera preview on Nexus 5X, please let the developers know about this - Android's developer relations folks are trying to reach out to apps as we find them, and LG is also helping out, but it might take a bit before everyone's up to speed on this issue.

    解决方法直接上代码:

    public int getCameraDisplayOrientation(Activity activity,
                                               int cameraId) {
            Camera.CameraInfo info = new Camera.CameraInfo();
            Camera.getCameraInfo(cameraId, info);
            int rotation = activity.getWindowManager().getDefaultDisplay().getRotation();
            int degrees = 0;
            switch (rotation) {
                case Surface.ROTATION_0:
                    degrees = 0;
                    break;
                case Surface.ROTATION_90:
                    degrees = 90;
                    break;
                case Surface.ROTATION_180:
                    degrees = 180;
                    break;
                case Surface.ROTATION_270:
                    degrees = 270;
                    break;
            }
    
            int result;
            if (info.facing == Camera.CameraInfo.CAMERA_FACING_FRONT) {
                result = (info.orientation + degrees) % 360;
                result = (360 - result) % 360;  // compensate the mirror
            } else {  // back-facing
                result = (info.orientation - degrees + 360) % 360;
            }
            return result;
        }
    

    上面代码获取摄像头预览偏转的角度,只需要通过setDisplayOrientation方法重新设置一下预览角度即可:

    rotation = getCameraDisplayOrientation(mContext, cameraFacing);
    mCamera.setDisplayOrientation(rotation);
    

    同时在播放拍摄好的视频时,也要注意设置输出角度,否则也会出现图像偏转问题

    mRecorder.setOrientationHint(360 - rotation);//输出角度
    

    视频预览尺寸设置,导致播放失败或播放模糊问题

    录制好的视频播放预览时,如果设置的播放尺寸手机不存在,会导致调用出错而无法播放视频,尺寸过小是也会出现播放模糊问题,解决方案是根据手机的硬件配置获取最合适的尺寸进行播放,代码如下:

    //获取摄像头支持的最接近的尺寸
    public Camera.Size getOptimalPreviewSize(List<Camera.Size> sizes, int w, int h) {
            final double ASPECT_TOLERANCE = 0.2;
            double targetRatio = (double) w / h;
            if (sizes == null) return null;
    
            Camera.Size optimalSize = null;
            double minDiff = Double.MAX_VALUE;
    
            int targetHeight = h;
    
            // Try to find an size match aspect ratio and size
            for (Camera.Size size : sizes) {
                double ratio = (double) size.width / size.height;
                if (Math.abs(ratio - targetRatio) > ASPECT_TOLERANCE) continue;
                if (Math.abs(size.height - targetHeight) < minDiff) {
                    optimalSize = size;
                    minDiff = Math.abs(size.height - targetHeight);
                }
            }
    
            // Cannot find the one match the aspect ratio, ignore the requirement
            if (optimalSize == null) {
                minDiff = Double.MAX_VALUE;
                for (Camera.Size size : sizes) {
                    if (Math.abs(size.height - targetHeight) < minDiff) {
                        optimalSize = size;
                        minDiff = Math.abs(size.height - targetHeight);
                    }
                }
            }
            return optimalSize;
        }
    
    Camera.Size recordSize = getOptimalPreviewSize(mCamera.getParameters().getSupportedPreviewSizes(), 640, 480);
    if (recordSize != null) {
                    //设置要捕获的视频的宽度和高度
                    mSurfaceHolder.setFixedSize(recordSize.width, recordSize.height);
                    mRecorder.setVideoSize(recordSize.width, recordSize.height);
                }
    

    相关文章

      网友评论

          本文标题:Android摄像头相关问题解决

          本文链接:https://www.haomeiwen.com/subject/cwvpdftx.html