Неустранимое исключение: java.lang.IllegalArgumentException: получатель не зарегистрирован: android.hardware.camera2.CameraManager - PullRequest
0 голосов
/ 26 сентября 2018

Я разрабатываю приложение для фонарика, которое включает / выключает системный тур.

У меня сбой, который отображается на Android M (v6.0) на

Crashlytics

Вот сведения о проблеме и трассировка стека:

Fatal Exception: java.lang.IllegalArgumentException: Receiver not registered: android.hardware.camera2.CameraManager$1@49e5f1b
   at android.app.LoadedApk.forgetReceiverDispatcher(LoadedApk.java:789)
   at android.app.ContextImpl.unregisterReceiver(ContextImpl.java:1222)
   at android.hardware.camera2.CameraManager$3.run(CameraManager.java:1266)
   at android.os.Handler.handleCallback(Handler.java:815)
   at android.os.Handler.dispatchMessage(Handler.java:104)
   at android.os.Looper.loop(Looper.java:207)
   at android.app.ActivityThread.main(ActivityThread.java:5728)
   at java.lang.reflect.Method.invoke(Method.java)
   at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:789)
   at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:679)

У меня есть следующие Manifest разрешения и аппаратные функции:

<uses-feature android:name="android.hardware.camera" />
<uses-feature android:name="android.hardware.camera.flash" />

и

<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.FLASHLIGHT" />

**** РЕДАКТИРОВАТЬ: ****

Вот код, который я использую для доступа к камере:

// Here, I am checking if SDK >= M
if (VersionUtils.isMarshmallowOrGreater()) {

        cameraManager = (CameraManager) getSystemService(Context.CAMERA_SERVICE);

        if (cameraManager != null) {

            try {
                cameraId = cameraManager.getCameraIdList()[0];
            } catch (CameraAccessException | ArrayIndexOutOfBoundsException e) {
                e.printStackTrace();
            }
        }

} else {

        if (camera == null || camera.getParameters() == null) {

            try {
                camera = Camera.open();
                params = camera.getParameters();
            } catch (RuntimeException e) {
                e.printStackTrace();
            }
        }

}

Вот код для включениявспышка / тур:

if (VersionUtils.isMarshmallowOrGreater()) {

            try {
                cameraManager.setTorchMode(cameraId, true);
            } catch (Exception e) {
                e.printStackTrace();
            }

 } else {

            if (camera == null || params == null || camera.getParameters() == null) {
                getCamera();
                return;
            }

            params = camera.getParameters();
            params.setFlashMode(Parameters.FLASH_MODE_TORCH);
            camera.setParameters(params);

            startCameraPreview();

 }

Также, вот код выключения вспышки камеры:

if (VersionUtils.isMarshmallowOrGreater()) {

            try {
                cameraManager.setTorchMode(cameraId, false);
            } catch (Exception e) {
                e.printStackTrace();
            }

 } else {

            if (camera == null || params == null || camera.getParameters() == null) {
                return;
            }

            try {

                params = camera.getParameters();
                params.setFlashMode(Parameters.FLASH_MODE_OFF);
                camera.setParameters(params);
                stopCameraPreview();
                camera.release();
                camera = null;

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

Код startCameraPreview() Метод:

private void startCameraPreview() {
    try {
        camera.startPreview();
    } catch (Exception e) {
        e.printStackTrace();
    }
}

У меня нет приложения в моем приложении, кроме класса провайдера виджетов, но у меня нет ни одной строки кода, которая делает (регистрирует / отменяет регистрацию) получателя !!

Я искал и прочитал много ссылокресурсы по этой проблеме, но я не смог найти какой-либо подсказки, чтобы точно знать строку, которая ее вызывала.

Кто-нибудь сталкивался с этой проблемой, ваша помощь приветствуется.

Ответы [ 3 ]

0 голосов
/ 30 сентября 2018

Camera.Parameters устарело на уровне API 21. Вместо этого используйте CameraManager.

Для setFlashMode (String value) в Camera.Parameters существует эквивалентный метод setTorchMode (String cameraId, boolean enabled) в CameraManager

0 голосов
/ 02 октября 2018

У меня была такая же проблема (или похожая).Моя трассировка стека была точно такой же, как ваша.Я решил свою проблему, убедившись (в коде моего приложения), что я не пытаюсь выключить горелку, если горелка не была включена моим приложением ранее.

Произошел сбой при вызовеcameraManager.setTorchMode(cameraId, false) два раза подряд.

Поэтому я просто поддерживаю логический флаг в моем приложении, который показывает точное состояние горелки на данный момент.Установите его в true сразу после cameraManager.setTorchMode(cameraId, true) вызова и не делайте cameraManager.setTorchMode(cameraId, false), если флаг не равен true.Установите флаг в значение false после успешного выполнения cameraManager.setTorchMode(cameraId, false).

Надеюсь, это поможет ...

0 голосов
/ 28 сентября 2018

Я думаю, что этот пост ( при попытке выключить светодиод камеры, сбой приложения ) полезен.

Короче, если вы попытаетесь снова отключить фонарик (даже если фонарик уже отключен)), приложение перестало работать.

...