I set a preference for users to select save folder for my app using Storage Access Framework. After getting uri onActivityResult
I save it to SharedPreferences
as String and save image when it's to be saved.
I'm using this method to save image successfully.
public void saveImageWithDocumentFile(String uriString, String mimeType, String name) {
isImageSaved = false;
try {
Uri uri = Uri.parse(uriString);
DocumentFile pickedDir = DocumentFile.fromTreeUri(this, uri);
DocumentFile file = pickedDir.createFile(mimeType, name);
OutputStream out = getContentResolver().openOutputStream(file.getUri());
isImageSaved = mBitmap.compress(CompressFormat.JPEG, 100, out);
out.close();
} catch (IOException e) {
throw new RuntimeException("Something went wrong : " + e.getMessage(), e);
}
Toast.makeText(MainActivity.this, "Image saved " + isImageSaved, Toast.LENGTH_SHORT).show();
}
If user deletes the folder selected using SAF, iget null DocumentFile file
and app crashes. My first question is how can i check if folder exist without opening SAF ui again.
I also want to use ParcelFileDescriptor to save same image with this method
public void saveImageWithParcelFileDescriptor(String folder, String name) {
if (mBitmap == null) {
Toast.makeText(MainActivity.this, "", Toast.LENGTH_SHORT).show();
return;
}
String image = folder + File.separator + name + ".jpg";
Toast.makeText(MainActivity.this, "image " + image, Toast.LENGTH_LONG).show();
Uri uri = Uri.parse(image);
ParcelFileDescriptor pfd = null;
FileOutputStream fileOutputStream = null;
try {
pfd = getContentResolver().openFileDescriptor(uri, "w");
fileOutputStream = new FileOutputStream(pfd.getFileDescriptor());
mBitmap.compress(CompressFormat.JPEG, 100, fileOutputStream);
} catch (FileNotFoundException e) {
e.printStackTrace();
} finally {
if (pfd != null) {
try {
pfd.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (fileOutputStream != null) {
try {
fileOutputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Toast.makeText(MainActivity.this, "Image saved " + isImageSaved, Toast.LENGTH_SHORT).show();
}
i get java.lang.IllegalArgumentException: Invalid URI: content://com.android.externalstorage.documents/tree/612E-B7BF%3Aname/imagePFD.jpg
on linepfd = getContentResolver().openFileDescriptor(uri, "w");
This is how I call this method, currentFolder is the folder I get using intent and same folder on first method.
saveImageWithParcelFileDescriptor(currentFolder, "imagePFD");
How can I fix this, and which method is more preferable and why?
how can i check if folder exist
DocumentFile
has an exists()
method. In theory, pickedDir.exists()
should tell you if it exists. In practice, it is up to the storage provider.
I also want to use ParcelFileDescriptor to save same image with this method
That code has bugs:
You cannot grant yourself permissions using grantUriPermission()
You cannot invent arbitrary Uri
values via concatenation, particularly for a provider that is not yours
How can I fix this
Delete it.
which method is more preferable
The first one.
and why?
The first one will work, perhaps with minor adjustment. The second one has no chance of working.