Android Java で CameraX の写真をキャプチャ3
![](https://www.sibainu.org/wordpress/wp-content/uploads/2024/03/sibainu20240302top-755x1024.jpg)
今回もよく頑張ったなと言ってくれいる柴犬です。
前回のアプリを実行
撮影後にトリガーされる画像キャプチャのリスナーを設定する imagecapture.takePicture から全く動きません。
エミュレートでは全く問題なく最後まで実行されましたが、動きません。
左が起動直後の画像で、右がシャッターボタン「Shutter」をタップして実行させたところです。
![](https://www.sibainu.org/wordpress/wp-content/uploads/2024/03/wp_run20240302-1.jpg)
やってみたこと
ContentValues の設定の見直し
// ContentValuesオブジェクトを生成。
ContentValues values = new ContentValues();
// 画像ファイル名を設定。
values.put(MediaStore.Images.Media.TITLE, name);
// 画像ファイルの表示名を設定。
values.put(MediaStore.Images.Media.DISPLAY_NAME, name);
// 画像ファイルの種類を設定。
values.put(MediaStore.Images.Media.MIME_TYPE, "image/jpeg");
// 共有ストレージに保存するパス
if (Build.VERSION.SDK_INT > Build.VERSION_CODES.P) {
values.put(MediaStore.Images.Media.RELATIVE_PATH, "Pictures/CameraX-Image");
}
ImageCapture.OutputFileOptions.Builder() の引数関係の見直し
// file + metadata 出力オプション・オブジェクトの作成
ImageCapture.OutputFileOptions outputOptions = new ImageCapture.OutputFileOptions.Builder(resolver,
MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
values).build();
imagecapture.takePicture の引数関係の見直し
// 撮影後にトリガーされる画像キャプチャのリスナーを設定する
imagecapture.takePicture(
outputOptions,
ContextCompat.getMainExecutor(this),
new ImageCapture.OnImageSavedCallback() {省略});
ここまで、いろいろやってみましたが大同小異で状況に変わりはありません。
次に、何かが邪魔をしているのではないかと考えました。
ContentValues values を適当な位置で削除することにしました。
values.clear();
を入れることにしました。
やりました最後まで実行されました。完了表示まで1秒もかかりませんでした。
![](https://www.sibainu.org/wordpress/wp-content/uploads/2024/03/wp_run20240302-2.jpg)
takePhoto
うまくいったコードです。
いろいろ触りましたのでごちゃごちゃしています。
private void takePhoto() { if (imagecapture == null) { return; } Log.d(TAG, "imagecapture"); tv.setText("キャプチャ・保存処理中"); // 一意の名前にしなければならないのでミリ秒までつかいます。 SimpleDateFormat dateFormat = new SimpleDateFormat(FILENAME_FORMAT, Locale.JAPAN); // 現在の日時を取得。 Date now = new Date(System.currentTimeMillis()); // 取得した日時データを「yyyyMMddHHmmssSSS」形式に整形した文字列を生成。 String nowStr = dateFormat.format(now); // ストレージに格納する画像のファイル名を生成。ファイル名の一意を確保するためにタイムスタンプの値を利用。 String name = "Photo_" + nowStr; Log.d(TAG,name); tv.setText("ファイル名 :" + name); //↓↓↓↓↓ ContentValuesオブジェクトを生成開始。 ContentValues values = new ContentValues(); // 画像ファイル名を設定。 values.put(MediaStore.Images.Media.TITLE, name); // 画像ファイルの表示名を設定。 values.put(MediaStore.Images.Media.DISPLAY_NAME, name); // 画像ファイルの種類を設定。 values.put(MediaStore.Images.Media.MIME_TYPE, "image/jpeg"); // 共有ストレージに保存するパス // P Constant Value: 28 if (Build.VERSION.SDK_INT > Build.VERSION_CODES.P) { //values.put(MediaStore.Images.Media.RELATIVE_PATH, "Pictures/CameraX-Image"); values.put(MediaStore.Images.Media.RELATIVE_PATH, Environment.DIRECTORY_PICTURES + "/CameraX-Image"); } //↑↑↑↑↑オブジェクトを生成終り Log.d(TAG,"共有ストレージパス"); // ContentResolverオブジェクトを生成。 ContentResolver resolver = getContentResolver(); Log.d(TAG,"resolver"); // ContentResolverを使って URI を取得(予約) imageuri = resolver.insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values); Log.d(TAG,"imageuri"); tv.setText("URI :" + imageuri.toString()); // file + metadata 出力オプションオブジェクトの作成 ImageCapture.OutputFileOptions outputOptions = new ImageCapture.OutputFileOptions.Builder( //resolver, getContentResolver(), MediaStore.Images.Media.EXTERNAL_CONTENT_URI, //imageuri, エラー values).build(); // これがないとキャプチャーでエラーになります。 values.clear(); Log.d(TAG,"outputOptions"); tv.setText("アウトプットオプション"); //シャッター音追 MediaActionSound sound = new MediaActionSound(); sound.load(MediaActionSound.SHUTTER_CLICK); // 撮影後にトリガーされる画像キャプチャのリスナーを設定する imagecapture.takePicture( outputOptions, //Executors.newSingleThreadExecutor(), ContextCompat.getMainExecutor(MainActivity.this), //キャプチャー処理がなされた後のコールバックオブジェクト new ImageCapture.OnImageSavedCallback() { @Override public void onError(ImageCaptureException e) { Log.e(TAG, "Photo capture failed: " + e.toString(), e); tv.setText("キャプチャーエラー"); } @Override public void onImageSaved(ImageCapture.OutputFileResults outputFileResults) { CharSequence msg = "Photo capture succeeded: " + outputFileResults.getSavedUri(); Log.d(TAG, msg.toString()); tv.setText(msg.toString()); // Uriの取得 Uri uri = Uri.parse(outputFileResults.getSavedUri().toString()); try { Log.d(TAG,"begin try"); InputStream ips = resolver.openInputStream(uri); Log.d(TAG,"InputStream"); //シャッター音の追加 sound.play(MediaActionSound.SHUTTER_CLICK); // アップロード非同期処理 FtpAccessC(name + ".jpg", ips); } catch (Exception ex) { Log.d(TAG, "アップロードエラー :", ex); } } }); }
NAS
NAS を見てみると確かに保存されています。
![](https://www.sibainu.org/wordpress/wp-content/uploads/2024/03/wp_nas20240302-1-1024x320.jpg)
今回ここまでとします。