I'm taking picture from camera and saving in a public folder(Pictures/myFolder) and I'm storing the Uri from picture to reload to my views, but I need build a File with real path, but I cant recover the path and all the codes they find on the internet give me null pointer, how can i recover the real path?
Uri example:
content://media/content://br.com.technolog.darwinchecklist.fileprovider/darwin_checklist_images/DARWIN_20180827_114154_460340375.jpg/images/media
Method that does not work
public String getRealPathFromURI(Uri uri) {
String path = "";
if (getContentResolver() != null) {
Cursor cursor = getContentResolver().query(uri, null, null, null, null);
if (cursor != null) {
cursor.moveToFirst();
int idx = cursor.getColumnIndex(MediaStore.Images.ImageColumns.DATA);
path = cursor.getString(idx);
cursor.close();
}
}
return path;
}
Ref: Get Real Path For Uri Android
getRealpathFromUri(Uri uri)
{
String[] filePathColumn = {MediaStore.Images.Media.DATA};
Cursor cursor = getContentResolver().query(uri, filePathColumn, null, null, null);
if (cursor == null)
{ // Source is Dropbox or other similar local file path
result = contentURI.getPath();
}
else
{
if(cursor.moveToFirst()){
int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
//String yourRealPath = cursor.getString(columnIndex);
path = cursor.getString(columnIndex);
}
cursor.close();
}
return path;
}
I'm using the following code to get the real path of a document from an Uri:
/**
* Retrieve filename from Uri
*
* #param uri Uri following the schemes: "file" or "content"
* #param contentResolver ContentResolver to resolve content scheme
*
* #return filename if operation succeded. Can be null.
*/
public static String getFileName(#NonNull final Uri uri, #NonNull final ContentResolver contentResolver) {
String filename = "";
if (ContentResolver.SCHEME_FILE.equals(uri.getScheme())) {
filename = uri.getLastPathSegment();
} else if (ContentResolver.SCHEME_CONTENT.equals(uri.getScheme())) {
try {
Cursor cursor = contentResolver.query(uri, null, null, null, null);
int index = cursor.getColumnIndex(OpenableColumns.DISPLAY_NAME);
cursor.moveToFirst();
filename = cursor.getString(index);
cursor.close();
} catch (Exception e) {
Log.e(TAG, "Exception when retrieving file name: " + e.getMessage());
}
}
return filename;
}
Related
I have two applications, one contains content provider and other app receives data using content resolver. If i add any data form provider that should be displayed from receiver in second app, this is the expected functionality.But after adding data once I remove first app from stack then second app displays null cursor,If I keep first app in stack, then second app displays correct value .(This issue only comes in one plus devices)
code snippet where cursor value coming null is,
Cursor c = getContentResolver().query(CONTENT_URI, null, null, null,
null);
may be it will help you
private String uriToFilename(Uri uri) {
String path = null;
if (Build.VERSION.SDK_INT < 11) {
path = getRealPathFromURI_BelowAPI11(this, uri);
} else if (Build.VERSION.SDK_INT < 19) {
path = getRealPathFromURI_API11to18(this, uri);
} else {
path = getRealPathFromURI_API19(this, uri);
}
return path;
}
BelowAPI11
public static String getRealPathFromURI_BelowAPI11(Context context, Uri contentUri) {
String[] proj = {MediaStore.Images.Media.DATA};
Cursor cursor = context.getContentResolver().query(contentUri, proj, null, null, null);
int column_index
= cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
cursor.moveToFirst();
return cursor.getString(column_index);
}
API11to18
public static String getRealPathFromURI_API11to18(Context context, Uri contentUri) {
String[] proj = {MediaStore.Images.Media.DATA};
String result = null;
CursorLoader cursorLoader = new CursorLoader(
context,
contentUri, proj, null, null, null);
Cursor cursor = cursorLoader.loadInBackground();
if (cursor != null) {
int column_index =
cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
cursor.moveToFirst();
result = cursor.getString(column_index);
}
return result;
}
API19
public static String getRealPathFromURI_API19(Context context, Uri uri) {
Log.e("uri", uri.getPath());
String filePath = "";
if (DocumentsContract.isDocumentUri(context, uri)) {
String wholeID = DocumentsContract.getDocumentId(uri);
Log.e("wholeID", wholeID);
// Split at colon, use second item in the array
String[] splits = wholeID.split(":");
if (splits.length == 2) {
String id = splits[1];
String[] column = {MediaStore.Images.Media.DATA};
// where id is equal to
String sel = MediaStore.Images.Media._ID + "=?";
Cursor cursor = context.getContentResolver().query(MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
column, sel, new String[]{id}, null);
int columnIndex = cursor.getColumnIndex(column[0]);
if (cursor.moveToFirst()) {
filePath = cursor.getString(columnIndex);
}
cursor.close();
}
} else {
filePath = uri.getPath();
}
return filePath;
}
Enable Don’t optimize inside Settings to resolve one plus issue.
Settings –> Battery –> Battery Optimization –> Your App –> Don’t optimize
enter image description here
I am starting an intent to pick a file, I do pick a file and I get a URI, which I obviously can't use.
I am trying to convert this Uri to a legit file path and for that I use this method
public string GetPathToImage(global::Android.Net.Uri uri)
{
string path = null;
// The projection contains the columns we want to return in our query.
string[] projection = new[] { global::Android.Provider.MediaStore.Images.Media.InterfaceConsts.Data };
using (global::Android.Database.ICursor cursor = ManagedQuery(uri, projection, null, null, null))
{
if (cursor != null)
{
int columnIndex = cursor.GetColumnIndexOrThrow(global::Android.Provider.MediaStore.Images.Media.InterfaceConsts.Data);
cursor.MoveToFirst();
path = cursor.GetString(columnIndex);
}
}
return path;
}
Problem: this method returns a null string. But I need a working one.
Any suggestions?
this is my code when i'm getting image from internal storage (gallery).
In lollipop file path return always null.
if (requestCode == PICK_IMAGE) {
if(resultCode == RESULT_OK){
//image successfully picked
// launching upload activity
Uri selectedImage = data.getData();
String[] filePathColumn = { MediaStore.Images.Media.DATA };
Cursor cursor = getContentResolver().query(selectedImage,filePathColumn, null, null, null);
cursor.moveToFirst();
columnindex = cursor.getColumnIndex(MediaStore.Images.Media.DATA);
file_path = cursor.getString(columnindex);
Log.d(getClass().getName(), "file_path"+file_path);
fileUri = Uri.parse("file://" + file_path);
cursor.close();
launchUploadActivity(true, PICK_IMAGE);
}else if (resultCode == RESULT_CANCELED) {
// user cancelled recording
Toast.makeText(getApplicationContext(),"User cancelled image selection", Toast.LENGTH_SHORT).show();
} else {
// failed to record video
Toast.makeText(getApplicationContext(),"Sorry! failed to pick image", Toast.LENGTH_SHORT).show();
}
Thanx all,I found the solution.
Uri selectedImage = data.getData();
String wholeID = DocumentsContract.getDocumentId(selectedImage);
// Split at colon, use second item in the array
String id = wholeID.split(":")[1];
String[] column = { MediaStore.Images.Media.DATA };
// where id is equal to
String sel = MediaStore.Images.Media._ID + "=?";
Cursor cursor = getContentResolver().
query(MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
column, sel, new String[]{ id }, null);
String filePath = "";
int columnIndex = cursor.getColumnIndex(column[0]);
if (cursor.moveToFirst()) {
filePath = cursor.getString(columnIndex);
}
cursor.close();
setImageFromIntent(filePath);
Add permission to your manifest -
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
you have to define read permission, before read any content.
EDITED
Update your code -
Uri selectedImage = data.getData();
String[] filePathColumn = { MediaStore.Images.Media.DATA };
Cursor cursor = getContentResolver().query(selectedImage,filePathColumn, null, null, null);
columnindex = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
cursor.moveToFirst();
file_path = cursor.getString(columnindex);
Log.d(getClass().getName(), "file_path"+file_path);
fileUri = Uri.parse("file://" + file_path);
cursor.close();
launchUploadActivity(true, PICK_IMAGE);
So here if any exception in getting data from cursor then it throws exception.
Lollipop decided to take another course with getting files from the system. (Some say it is from KitKat, but I haven't encountered it yet on KitKat). The code below is to get the filepath on lollipop
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT && isMediaDocument(uri))
{
final String docId = DocumentsContract.getDocumentId(uri);
final String[] split = docId.split(":");
final String type = split[0];
Uri contentUri = null;
if ("image".equals(type))
{
contentUri = MediaStore.Audio.Media.EXTERNAL_CONTENT_URI;
}
final String selection = "_id=?";
final String[] selectionArgs = new String[] {
split[1]
};
String filePath = getDataColumn(context, contentUri, selection, selectionArgs);
}
isMediaDocument:
public static boolean isMediaDocument(Uri uri)
{
return "com.android.providers.media.documents".equals(uri.getAuthority());
}
getDataColumn:
private static String getDataColumn(Context context, Uri uri, String selection, String[] selectionArgs)
{
Cursor cursor = null;
final String column = "_data";
final String[] projection = {
column
};
try {
cursor = context.getContentResolver().query(uri, projection, selection, selectionArgs, null);
if (cursor != null && cursor.moveToFirst())
{
final int column_index = cursor.getColumnIndexOrThrow(column);
return cursor.getString(column_index);
}
} finally {
if (cursor != null)
cursor.close();
}
return null;
}
If you still have problems, this is the full answer that checks for images, audio, video, files, etc.
///////////////////create file obj:
private File mFileTemp;
String state = Environment.getExternalStorageState();
if (Environment.MEDIA_MOUNTED.equals(state)) {
mFileTemp = new File(Environment.getExternalStorageDirectory(), InternalStorageContentProvider.TEMP_PHOTO_FILE_NAME);
}
else {
mFileTemp = new File(getFilesDir(), InternalStorageContentProvider.TEMP_PHOTO_FILE_NAME);
}
/////////////////// use in start activity for result
try {
InputStream inputStream = getContentResolver().openInputStream(data.getData());
FileOutputStream fileOutputStream = new FileOutputStream(mFileTemp);
copyStream(inputStream, fileOutputStream);
fileOutputStream.close();
inputStream.close();
imagepath = mFileTemp.getPath();
} catch (Exception e) {
Log.e("TAG", "Error while creating temp file", e);
}
/////////////////
public static void copyStream(InputStream input, OutputStream output)
throws IOException
{
byte[] buffer = new byte[1024];
int bytesRead;
while ((bytesRead = input.read(buffer)) != -1)
{
output.write(buffer, 0, bytesRead);
}
}
public void String(Uri file_uri){
String path = null;
Cursor returnCursor = getContext().getContentResolver().query(file_uri, null,
null, null, null);
if (returnCursor != null && returnCursor.moveToFirst()) {
//to get file name
int nameIndex =
returnCursor.getColumnIndex(OpenableColumns.DISPLAY_NAME);
//string filename will get a filename which you have choosen
String fileName = returnCursor.getString(nameIndex);
//to get full path of image
path = returnCursor.getString(returnCursor.getColumnIndex(MediaStore.MediaColumns.DATA));
}
return path;
}
In application I am using cursorloader to get captures image file path, it always returns null:
Uri file path = file:///storage/emulated/0/Pictures/BBI_Images/BBI_ORIG_20150313_112912.jpg
public static int getRotation(Context context, Uri selectedImage, String filePath) {
try{
String[] projection = { MediaStore.Images.Media.DATE };
CursorLoader loader = new CursorLoader(context, selectedImage, projection, null, null, null);
Cursor cursor = loader.loadInBackground();//here i can get only null
cursor.moveToFirst();
int column_index_data = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
int rotation = 0;
String realPath = cursor.getString(column_index_data);
if (realPath != null) {
rotation = getRotationForImage(realPath);
}
return rotation;
}catch(Exception e){
e.printStackTrace();
}
return 0;
}
I would like to upload file to server. So I use a file chooser. But I have a problem with some application to get the real path from uri. the case if the content is a v
ideo, audio or image or if I can get the path directly i have no problem. the methode imlemented are :
public String getRealAudioPathFromURI(Uri contentUri) {
String[] proj = { MediaStore.Audio.Media.DATA };
//This method was deprecated in API level 11
//Cursor cursor = managedQuery(contentUri, proj, null, null, null);
CursorLoader cursorLoader = new CursorLoader(
this,
contentUri, proj, null, null, null);
Cursor cursor = cursorLoader.loadInBackground();
int column_index =
cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.DATA);
cursor.moveToFirst();
return cursor.getString(column_index);
}
and it is the some for image and video. but my problem is when content is in this forme:
content://com.dataviz.dxtg.documentprovider/document/file%3A%2F%2F%2Fmnt%2Fsdcard%2FDownload%2Arbres.png
I tried the method
private String getFilePathFromContentUri(Uri selectedVideoUri,
ContentResolver contentResolver) {
String filePath;
String[] filePathColumn = {MediaStore.MediaColumns.DATA};
Cursor cursor = contentResolver.query(selectedVideoUri, filePathColumn, null, null, null);
cursor.moveToFirst();
int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
filePath = cursor.getString(columnIndex);
cursor.close();
return filePath;
}
So how to get the real path from URi and if there is an other content type .
to get my real path is given below:
//Uri return from external activity
orgUri = data.getData();
text1.setText("fichier à envoyer " + orgUri.toString() + "\n");
// imagepath = orgUri.toString() ;
//path converted from Uri
//convertedPath = orgUri.getPath();
if(orgUri.toString().contains(IMAGEMEDIA)){
convertedPath = getRealPathFromURI(orgUri);
} else if(orgUri.toString().contains(AUDIOMEDIA)){
convertedPath = getRealAudioPathFromURI(orgUri);
}
else if(orgUri.toString().contains(VIDEOMEDIA)){
convertedPath = getRealvideoPathFromURI(orgUri);
}else {
if(orgUri.toString().contains("content")){
convertedPath = getFilePathFromContentUri(orgUri,
getApplicationContext().getContentResolver());
} else {
convertedPath = orgUri.getPath();
}
}
try this one
Uri selectedFile = data.getData();
String path = selectedFile.getPath();
it works for me.
if it is not than let me inform i have another way too
This works for me...
public static String getPath(final Context context, final Uri uri) {
final boolean isKitKat = Build.VERSION.SDK_INT >=
Build.VERSION_CODES.KITKAT;
Log.i("URI",uri+"");
String result = uri+"";
// DocumentProvider
// if (isKitKat && DocumentsContract.isDocumentUri(context, uri)) {
if (isKitKat && (result.contains("media.documents"))) {
String[] ary = result.split("/");
int length = ary.length;
String imgary = ary[length-1];
final String[] dat = imgary.split("%3A");
final String docId = dat[1];
final String type = dat[0];
Uri contentUri = null;
if ("image".equals(type)) {
contentUri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
} else if ("video".equals(type)) {
} else if ("audio".equals(type)) {
}
final String selection = "_id=?";
final String[] selectionArgs = new String[] {
dat[1]
};
return getDataColumn(context, contentUri, selection, selectionArgs);
}
else
if ("content".equalsIgnoreCase(uri.getScheme())) {
return getDataColumn(context, uri, null, null);
}
// File
else if ("file".equalsIgnoreCase(uri.getScheme())) {
return uri.getPath();
}
return null;
}
public static String getDataColumn(Context context, Uri uri, String selection,
String[] selectionArgs) {
Cursor cursor = null;
final String column = "_data";
final String[] projection = {
column
};
try {
cursor = context.getContentResolver().query(uri, projection, selection, selectionArgs,
null);
if (cursor != null && cursor.moveToFirst()) {
final int column_index = cursor.getColumnIndexOrThrow(column);
return cursor.getString(column_index);
}
} finally {
if (cursor != null)
cursor.close();
}
return null;
}
It is a problem of decode. So the Solution is to add decode to the method. as given below:
private String getFilePathFromContentUri(Uri selectedVideoUri,
ContentResolver contentResolver) throws UnsupportedEncodingException {
String filePath;
String[] filePathColumn = {MediaStore.MediaColumns.DATA};
Cursor cursor = contentResolver.query(selectedVideoUri, filePathColumn, null, null, null);
cursor.moveToFirst();
int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
filePath = cursor.getString(columnIndex);
cursor.close();
String result = java.net.URLDecoder.decode(filePath, "UTF-8");
return result;
}
my onActivityResult:
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if(resultCode == RESULT_OK){
//image.setImageBitmap(null);
//Uri return from external activity
orgUri = data.getData();
text1.setText("fichier à envoyer " + orgUri.toString() + "\n");
// imagepath = orgUri.toString() ;
//path converted from Uri
//convertedPath = orgUri.getPath();
if(orgUri.toString().contains(IMAGEMEDIA)){
convertedPath = getRealPathFromURI(orgUri);
} else if(orgUri.toString().contains(AUDIOMEDIA)){
convertedPath = getRealAudioPathFromURI(orgUri);
}
else if(orgUri.toString().contains(VIDEOMEDIA)){
convertedPath = getRealvideoPathFromURI(orgUri);
}else {
if(orgUri.toString().contains("content")){
try {
convertedPath = getFilePathFromContentUri(orgUri,
getApplicationContext().getContentResolver());
} catch (UnsupportedEncodingException e) {
e.printStackTrace(); //To change body of catch statement use File | Settings | File Templates.
}
} else {
convertedPath = orgUri.getPath();
}
}
// text2.setText("Real Path: " + convertedPath + "\n");
imagepath = convertedPath;
uriFromPath = Uri.fromFile(new File(convertedPath));
}
}