Androidのカメラ起動時にエラーが発生で何も起こらないときの対処法
環境:M1 Mac mini / macOS: Big Sur
Androidでカメラ起動時にエラー発生
「[ERROR:flutter/lib/ui/ui_dart_state.cc(186)] Unhandled Exception: PlatformException(no_available_camera, No cameras available for taking pictures., null, null)」
「[ERROR:flutter/lib/ui/ui_dart_state.cc(186)] Unhandled Exception: PlatformException(no_available_camera, No cameras available for taking pictures., null, null)」
ヒーラー
Flutterの教材どおりのコードなのだが、環境の影響があるのかもしれない
ありがたいことにAndroidでは実機を使わずとも、エミュレーターでも擬似的にカメラを撮影することができます。そのカメラの起動時にエラーが発生しました。
問題
Flutterで作成したアプリで、カメラ撮影した写真を取得する機能におけるカメラ起動時にエラーが発生しました。
現象としては、カメラ起動ボタンを押して、許可を求めるダイアログが表示されるので許可したあと、元の画面に戻ってカメラは起動しないという挙動でした。クラッシュは起きません。
また、iOSの方は問題なく動作しました。
以下のエラーログが出ていました。
E/flutter ( 9937): [ERROR:flutter/lib/ui/ui_dart_state.cc(186)] Unhandled Exception: PlatformException(no_available_camera, No cameras available for taking pictures., null, null)
E/flutter ( 9937): #0 StandardMethodCodec.decodeEnvelope (package:flutter/src/services/message_codecs.dart:597:7)
E/flutter ( 9937): #1 MethodChannel._invokeMethod (package:flutter/src/services/platform_channel.dart:158:18)
E/flutter ( 9937): <asynchronous suspension>
E/flutter ( 9937): #2 MethodChannelImagePicker.pickImage (package:image_picker_platform_interface/src/method_channel/method_channel_image_picker.dart:30:19)
E/flutter ( 9937): <asynchronous suspension>
E/flutter ( 9937): #3 ...
E/flutter ( 9937): <asynchronous suspension>
E/flutter ( 9937):
解決方法
結論としては、Androidバージョンアップによる権限周りの仕様変更が影響していました。
該当のアプリはAndroidのターゲットバージョンを30「targetSdkVersion 30」にしています。
targetSdkVersion 30(Android10)以上の場合、Androidアプリがカメラの機能にアクセスするためには、AndroidManifest.xmlに以下のようなqueriesを定義する必要があります。
(uses-featureのパーミッションではない)
これで無事カメラの起動が確認できました。
ちなみに、以下のようなパーミッションの指定でも動きます。
<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.sample">
<uses-permission android:name="android.permission.QUERY_ALL_PACKAGES"/>
<!-- 省略 -->
</manifest>
しかし、必要な権限がカメラのアクセスのみであるとなると、QUERY_ALL_PACKAGESは相応しくありませんので、前述の解決方法が良いでしょう。
Flutterのエラーとして調べたのですが、Androidのエラーとして調査すれば、もっと早く解決できたかもしれません。