前提・実現したいこと
Androidのdevelopersドキュメントの
「CameraXを使ってみる」https://codelabs.developers.google.com/codelabs/camerax-getting-started/#0
「CameraX設定」https://developer.android.com/training/camerax/configuration?hl=ja
を参考にして、画像キャプチャで撮影して、指定した画像サイズで保存する処理をKotlinで書いていますが、指定した画像サイズで保存されずに、スマホカメラの最大値のサイズで保存されてしまいます。
指定した画像サイズで保存する方法をご教示ください。
発生している問題・エラーメッセージ
エラーメッセージは表示されません。 Logcatでも特にエラーの表示はありませんでした。 設定した画像サイズは、640 × 480 や 1280 x 720 ですが、どれを指定しても ストレージに保存された写真のサイズは、3264 x 2448 でした。
該当のソースコード
Kotlin
1class PhotoShootActivity : AppCompatActivity() { 2 … 省略 3 4 //プレビューと画像キャプチャのユースケースを実装 5 // 以前の★4.View を作成するとき…と、★5.カメラを選択し…が以下に統合 6 private fun startCamera() { 7 //★3.CameraProviderをリクエストするで追加 8 // ProcessCameraProviderは、カメラのライフサイクルをライフサイクル所有者にバインドするために使用 9 val cameraProviderFuture = ProcessCameraProvider.getInstance(this) 10 11 // //★4.View を作成するとき、CameraProviderが利用可能かどうかを確認 12 // リスナーをcameraProviderFutureに追加します。Runnableを1つの引数として追加します。 13 cameraProviderFuture.addListener(Runnable { 14 // Used to bind the lifecycle of cameras to the lifecycle owner 15 // Runnableでは、ProcessCameraProviderを追加、 16 // これは、アプリケーションプロセス内LifecycleOwnerにカメラのライフサイクルを結合するために使用 17 val cameraProvider: ProcessCameraProvider = cameraProviderFuture.get() 18 19 //★5.カメラを選択してライフサイクルとユースケースをバインドします。 20 // 5-1 Preview を作成します。 Preview オブジェクトを初期化 21 preview = Preview.Builder().build() 22 23 // Paste image capture code here! 24 //アプリの写真撮影カメラを設定 25 imageCapture = ImageCapture.Builder() 26 .setTargetRotation(previewView.display.rotation) 27 .build() 28 29 // CameraSelectorオブジェクトを作成 Select back camera 30 // 5-2 希望のカメラの LensFacing オプションを指定します。 31 // CameraSelector.Builder.requireLensFacingメソッドを使用して、 好みのレンズを渡します。 32 val cameraSelector = CameraSelector.Builder().requireLensFacing(CameraSelector.LENS_FACING_BACK).build() 33 34 //撮影時の解像度を指定する 35 val imageAnalysis = ImageAnalysis.Builder() 36 .setTargetResolution(Size(1280, 720)) 37 .build() 38 39 // tryブロックを作成します。 40 // そのブロック内で、cameraProviderに何もバインドされていないことを確認してから、 41 // プレビューオブジェクトをバインドします。 42 try { 43 // Unbind use cases before rebinding 44 cameraProvider.unbindAll() 45 46 // 5-3 選択したカメラとユースケースをライフサイクルにバインドします。 47 camera = cameraProvider.bindToLifecycle(this, cameraSelector, imageCapture, imageAnalysis, preview) 48 // 5-4 Preview を プレビュー画面XMLタグ(previewView)PreviewView に接続します。 49 preview?.setSurfaceProvider(previewView.createSurfaceProvider(camera?.cameraInfo)) 50 } 51 52 //アプリがフォーカスされていない場合など、このコードが失敗する原因はいくつかあります。 53 //catchブロックで囲み、障害が発生した場合にログに記録 54 catch(exc: Exception) { 55 Log.e(TAG, "Use case binding failed", exc) 56 } 57 58 }, ContextCompat.getMainExecutor(this)) 59 } 60 61 //画像キャプチャで撮影して保存 62 private fun takePhoto() { 63 // Get a stable reference of the modifiable image capture use case 64 // 画像キャプチャが設定される前に写真ボタンをタップすると、imageCaptureはnullになります。 65 // このreturn文がないと、アプリはクラッシュするので、NULLチェック。 66 val imageCapture = imageCapture ?: return 67 68 // 画像を保持するファイル名をtimestampで作成 69 val photoFile = File( 70 outputDirectory, 71 SimpleDateFormat(FILENAME_FORMAT, Locale.US 72 ).format(System.currentTimeMillis()) + ".jpg") 73 74 // Create output options object which contains file + metadata 75 // 出力をどのようにするかについて指定できるOutputFileOptionsオブジェクトを作成します。 76 // 上記のphotoFileに出力するので、photoFileを指定 77 val outputOptions = ImageCapture.OutputFileOptions.Builder(photoFile).build() 78 79 // Setup image capture listener which is triggered after photo has been taken 80 // imageCaptureオブジェクトのtakePicture()の呼び出し。 81 // 画像を保存するためのoutputOptions、executor、およびコールバックを渡します。 82 imageCapture.takePicture( 83 outputOptions, ContextCompat.getMainExecutor(this), object : ImageCapture.OnImageSavedCallback { 84 // イメージキャプチャが失敗、イメージキャプチャの保存が失敗した場合のエラーケースを追加 85 // 失敗したことをログに記録 86 override fun onError(exc: ImageCaptureException) { 87 Log.e(TAG, "Photo capture failed: ${exc.message}", exc) 88 } 89 // 正常なら前に作成したファイルに写真を保存し、成功したことをユーザーに知らせるトーストを提示 90 // ログステートメントを記録 91 override fun onImageSaved(output: ImageCapture.OutputFileResults) { 92 val savedUri = Uri.fromFile(photoFile) 93 94 // 成功したことをユーザーに知らせるトーストを提示 95 val msg = "写真撮影成功!: $savedUri" 96 Toast.makeText(baseContext, msg, Toast.LENGTH_SHORT).show() 97 // ログステートメントを記録 98 val msg2 = "Photo capture succeeded: $savedUri" 99 Log.d(TAG, msg2) 100 } 101 }) 102 } 103 104}
試したこと
・デバッグモードでアプリを起動して、実行状況を確認しましたが、
選択したカメラとユースケースをライフサイクルにバインドする処理
camera = cameraProvider.bindToLifecycle(this, cameraSelector, imageCapture, imageAnalysis, preview)
で、撮影時の解像度imageAnalysisを指定しているにもかかわらず、指定したとおりに保存されません。
そもそも、保存時の出力画像には反映されないのでしょうか?
別途、保存時に画像のリサイズの処理が必要でしょうか?
補足情報(FW/ツールのバージョンなど)
Language : Kotlin
Minimum API level :API 22: Android 5.1 (Lollipop)
Android Studio 4.0
Build #AI-193.6911.18.40.6514223, built on May 21, 2020
Runtime version: 1.8.0_242-release-1644-b01 amd64
VM: OpenJDK 64-Bit Server VM by JetBrains s.r.o
Windows 10 10.0
スマホ実機 機種
Plus One Japan Limited FTJ152A
Androidバージョン 5.1
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2022/05/16 07:21