OutputFileResults.getSavedUri

817 views
Skip to first unread message

Peter Varga

unread,
Sep 5, 2021, 12:07:27 PM9/5/21
to Android CameraX Discussion Group
I use CameraX and so far it works very well. However, now I must update my codes to Android Q and use the MediaStore library.
It seemed easy, since takePicture and startRecording returns with OutputResult, which has getSavedUri() to return the URI of the picture (video) taken.
However I could not find any working way to use this URI.
If I pass it to ContentResolver to open an InputStream I get a FileNotFoundException and says "open failed: ENOENT (No such file or directory)".

When I check in a file explorer I can find and open the image but in my app I can't (at least by using the URI). 

What is the way to open (and read) the image that camera just created?

Thanks in advance,
Peter

tonyt...@google.com

unread,
Sep 6, 2021, 2:23:36 AM9/6/21
to Android CameraX Discussion Group, varga.pet...@gmail.com
Hi,
Thanks for the question. Have you given the read permission?
Also how did you configure the OutputFileOptions? Did you use the MediaStore settings (ContentResolver, Uri, ContentValues)?

Peter Varga

unread,
Sep 6, 2021, 5:27:06 AM9/6/21
to Android CameraX Discussion Group, tonyt...@google.com, Peter Varga
Hi, 
Thanks for the quick answer.
These permissions are given (and others, not related to storage):
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.ACCESS_MEDIA_LOCATION" />

OutputFileOptions are created like this:
final ContentValues contentValues = new ContentValues();
contentValues.put(MediaStore.Video.Media.TITLE, fileName.fileName);
contentValues.put(MediaStore.Video.Media.DISPLAY_NAME, fileName.fileName);
contentValues.put(MediaStore.MediaColumns.RELATIVE_PATH, Environment.DIRECTORY_DCIM + File.separator + fileName.folderName);
contentValues.put(MediaStore.MediaColumns.MIME_TYPE, "image/jpeg");
ImageCapture.Metadata metadata = new ImageCapture.Metadata();
metadata.setReversedHorizontal(getLensFacing() == CameraSelector.LENS_FACING_FRONT);
OutputFileOptions outputFileOptions = new ImageCapture.OutputFileOptions.Builder(
        context.getContentResolver(),
        MediaStorage.getMediaUri(),
        contentValues)
      .setMetadata(metadata)
      .build();

Then I save OutputFileResults.getSavedUri().getPath() value. (String path = outputFileResults.getSavedUri().getPath())

When I try to open the image I try this:
final Bitmap originalBitmap = BitmapFactory.decodeStream(context.getContentResolver().openInputStream(Uri.parse(path)));

If I simply use the code above I get the following error:
W/System.err: java.io.FileNotFoundException: No content provider: /external/images/media/100891
(of course the path is different each time)

If I try to put "file://" before the path when creating the uri I get FileNotFoundException and says "open failed: ENOENT (No such file or directory)".

How should I use the path value? Is there any java example? I found only examples to recreate the whole stuff (using the real file name and creating contentValues and so on) but then what is the path we get in OutputFileResults?

Thanks in advance,
Peter

Leo Huang

unread,
Sep 6, 2021, 10:51:30 PM9/6/21
to Peter Varga, Android CameraX Discussion Group, tonyt...@google.com
Hi 
Looks like the scheme "content:/" of Uri has been removed.

   W/System.err: java.io.FileNotFoundException: No content provider: /external/images/media/100891

It should be content://external/images/media/100891

You don't have to call Uri.getPath(). i.e. outputFileResults.getSavedUri().getPath(), and just try to use the Uri directly.

ex: 
Uri uri = outputFileResults.getSavedUri();

context.getContentResolver().openInputStream(uri)

Peter Varga <varga.pet...@gmail.com> 於 2021年9月6日 週一 下午5:27寫道:
--
You received this message because you are subscribed to the Google Groups "Android CameraX Discussion Group" group.
To unsubscribe from this group and stop receiving emails from it, send an email to camerax-develop...@android.com.
To view this discussion on the web visit https://groups.google.com/a/android.com/d/msgid/camerax-developers/9d1c46e1-bbc9-4a59-ade3-89f7c37aa7e5n%40android.com.

Peter Varga

unread,
Sep 7, 2021, 7:21:47 AM9/7/21
to Android CameraX Discussion Group, leoh...@google.com, Android CameraX Discussion Group, tonyt...@google.com, Peter Varga
Thanks for your answer, it helped.
Some notes:

"You don't have to call Uri.getPath(). i.e. outputFileResults.getSavedUri().getPath(), and just try to use the Uri directly."
That's true when you immediately use the url after saving the image. But if you need to save it, the only chance is to get the path.

And the real uri should look like: content://media/external/images/media/100891

This is how it works.

Peter

Leo Huang

unread,
Sep 7, 2021, 10:25:06 AM9/7/21
to Peter Varga, Android CameraX Discussion Group, tonyt...@google.com
Oh, didn't notice that getPath() removes much more than that.

You are right the complete Uri should be content://media/external/images/media/100891.

Thanks for the info and glad that this works.

Peter Varga <varga.pet...@gmail.com> 於 2021年9月7日 週二 下午7:21寫道:
Reply all
Reply to author
Forward
0 new messages