java.lang.IllegalArgumentException:错误的参数传递给Lollipop上的相机服务

时间:2018-08-04 06:55:11

标签: android android-5.0-lollipop android-camera2 flashlight

我正在开发一个需要在android Lollipop(API 21、22)中打开闪光灯的应用程序

但是当我运行它时。

它显示自吹错误,所以我用Google搜索并找到了这个link,但我不明白如何解决问题!

FATAL EXCEPTION: main
Process: com.example.amir133.flashlight, PID: 15787
java.lang.IllegalArgumentException: Bad argument passed to camera service
    at android.hardware.camera2.utils.CameraBinderDecorator.throwOnError(CameraBinderDecorator.java:114)
    at android.hardware.camera2.utils.CameraBinderDecorator$CameraBinderDecoratorListener.onAfterInvocation(CameraBinderDecorator.java:73)
    at android.hardware.camera2.utils.Decorator.invoke(Decorator.java:81)
    at java.lang.reflect.Proxy.invoke(Proxy.java:397)
    at $Proxy1.createDefaultRequest(Unknown Source)
    at android.hardware.camera2.impl.CameraDeviceImpl.createCaptureRequest(CameraDeviceImpl.java:481)
    at com.example.amir133.flashlight.FlashLightUtilForL$MyCameraDeviceStateCallback.onOpened(FlashLightUtilForL.java:50)
    at android.hardware.camera2.impl.CameraDeviceImpl$1.run(CameraDeviceImpl.java:118)
    at android.os.Handler.handleCallback(Handler.java:739)
    at android.os.Handler.dispatchMessage(Handler.java:95)
    at android.os.Looper.loop(Looper.java:135)
    at android.app.ActivityThread.main(ActivityThread.java:5254)
    at java.lang.reflect.Method.invoke(Native Method)
    at java.lang.reflect.Method.invoke(Method.java:372)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:902)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:697)

问题似乎出在mBuilder = mCameraDevice.createCaptureRequest(CameraDevice.TEMPLATE_MANUAL);

我的设备也有闪光灯,并且我设置了摄像头权限

我的课:

public class FlashLightUtilForL {
private CameraCaptureSession mSession;
private CaptureRequest.Builder mBuilder;
private CameraDevice mCameraDevice;
private CameraManager mCameraManager;

@SuppressLint("MissingPermission")
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
public FlashLightUtilForL(Context context) {
    try {
        mCameraManager = (CameraManager) context.getSystemService(Context.CAMERA_SERVICE);
        mCameraManager.openCamera("0", new MyCameraDeviceStateCallback(), null);

    } catch (Exception e) {
        e.printStackTrace();
    }
}

@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
class MyCameraDeviceStateCallback extends CameraDevice.StateCallback {

    @Override
    public void onOpened(CameraDevice camera) {
        mCameraDevice = camera;
        try {

            mBuilder = mCameraDevice.createCaptureRequest(CameraDevice.TEMPLATE_MANUAL);
            List<Surface> list = new ArrayList<Surface>();
            Size size = getSmallestSize(mCameraDevice.getId());
            SurfaceTexture mSurfaceTexture = new SurfaceTexture(1);

            mSurfaceTexture.setDefaultBufferSize(size.getWidth(), size.getHeight());
            Surface mSurface = new Surface(mSurfaceTexture);
            list.add(mSurface);
            mBuilder.addTarget(mSurface);
            camera.createCaptureSession(list, new MyCameraCaptureSessionStateCallback(), null);
        } catch (CameraAccessException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void onDisconnected(CameraDevice camera) {

    }

    @Override
    public void onError(CameraDevice camera, int error) {

    }
}

@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
private Size getSmallestSize(String cameraId) throws CameraAccessException {
    Size[] outputSizes = mCameraManager.getCameraCharacteristics(cameraId)
            .get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP)
            .getOutputSizes(SurfaceTexture.class);
    if (outputSizes == null || outputSizes.length == 0) {
        throw new IllegalStateException(
                "Camera " + cameraId + "doesn't support any outputSize.");
    }
    Size chosen = outputSizes[0];
    for (Size s : outputSizes) {
        if (chosen.getWidth() >= s.getWidth() && chosen.getHeight() >= s.getHeight()) {
            chosen = s;
        }
    }
    return chosen;
}

/**
 * session callback
 */
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
class MyCameraCaptureSessionStateCallback extends CameraCaptureSession.StateCallback {

    @RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
    @Override
    public void onConfigured(CameraCaptureSession session) {
        mSession = session;
        try {
            mSession.setRepeatingRequest(mBuilder.build(), null, null);
        } catch (CameraAccessException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void onConfigureFailed(CameraCaptureSession session) {

    }
}

@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
public void turnOnFlashLight() {
    try {
        if(mBuilder!= null) {
            mBuilder.set(CaptureRequest.FLASH_MODE, CameraMetadata.FLASH_MODE_TORCH);
            mSession.setRepeatingRequest(mBuilder.build(), null, null);
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
}

@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
public void turnOffFlashLight() {
    try {
        mBuilder.set(CaptureRequest.FLASH_MODE, CameraMetadata.FLASH_MODE_OFF);
        mSession.setRepeatingRequest(mBuilder.build(), null, null);
    } catch (Exception e) {
        e.printStackTrace();
    }
}

public void close() {
    if (mCameraDevice == null || mSession == null) {
        return;
    }
    mSession.close();
    mCameraDevice.close();
    mCameraDevice = null;
    mSession = null;
}
}

1 个答案:

答案 0 :(得分:0)

尝试将TEMPLATE_STILL_CAPTURE作为模板值传递。

因此,除DEPTH_OUTPUT设备(如Google文档中提到的向后兼容)之外的所有相机设备均支持此模板。

这是link