Получить содержимое URI из пути к файлу в Android
Я знаю абсолютный путь изображения (например, /sdcard/cats.jpg). Есть ли способ содержания URI для этого файла?
На самом деле в моем коде я загружаю изображение и сохраняю его в определенном месте. Чтобы установить изображение в ImageView в настоящее время, я открываю файл, используя путь, получаю байты и создаю растровое изображение, а затем устанавливаю растровое изображение в ImageView. Это очень медленный процесс, вместо этого, если бы я мог получить содержимое URI, то я мог бы очень легко использовать метод ImageView.setImageUri(uri)
8 ответов
Попробуйте с:
ImageView.setImageURI(Uri.fromFile(new File("/sdcard/cats.jpg")));
Или с:
ImageView.setImageURI(Uri.parse(new File("/sdcard/cats.jpg").toString()));
ОБНОВИТЬ
Здесь предполагается, что ваши медиафайлы (изображения / видео) уже добавлены в контент-провайдера. Если нет, то вы не сможете получить URL-адрес содержимого точно таким, каким вы хотите. Вместо этого будет файл Uri.
У меня был такой же вопрос для моей файловой активности. Вы должны знать, что contenturi для файла поддерживает только такие медиасторские данные, как изображения, аудио и видео. Я даю вам код для получения изображения URI от выбора изображения из SDCard. Попробуйте этот код, может быть, он будет работать для вас...
public static Uri getImageContentUri(Context context, File imageFile) {
String filePath = imageFile.getAbsolutePath();
Cursor cursor = context.getContentResolver().query(
MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
new String[] { MediaStore.Images.Media._ID },
MediaStore.Images.Media.DATA + "=? ",
new String[] { filePath }, null);
if (cursor != null && cursor.moveToFirst()) {
int id = cursor.getInt(cursor.getColumnIndex(MediaStore.MediaColumns._ID));
cursor.close();
return Uri.withAppendedPath(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, "" + id);
} else {
if (imageFile.exists()) {
ContentValues values = new ContentValues();
values.put(MediaStore.Images.Media.DATA, filePath);
return context.getContentResolver().insert(
MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);
} else {
return null;
}
}
}
Принятое решение, вероятно, является лучшим выбором для ваших целей, но на самом деле ответит на вопрос в строке темы:
В моем приложении я должен получить путь из URI и получить URI из путей. Бывший:
/**
* Gets the corresponding path to a file from the given content:// URI
* @param selectedVideoUri The content:// URI to find the file path from
* @param contentResolver The content resolver to use to perform the query.
* @return the file path as a string
*/
private String getFilePathFromContentUri(Uri selectedVideoUri,
ContentResolver contentResolver) {
String filePath;
String[] filePathColumn = {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;
}
Последний (который я делаю для видео, но также может быть использован для аудио или файлов или других типов хранимого контента, заменив MediaStore.Audio (и т. Д.) На MediaStore.Video):
/**
* Gets the MediaStore video ID of a given file on external storage
* @param filePath The path (on external storage) of the file to resolve the ID of
* @param contentResolver The content resolver to use to perform the query.
* @return the video ID as a long
*/
private long getVideoIdFromFilePath(String filePath,
ContentResolver contentResolver) {
long videoId;
Log.d(TAG,"Loading file " + filePath);
// This returns us content://media/external/videos/media (or something like that)
// I pass in "external" because that's the MediaStore's name for the external
// storage on my device (the other possibility is "internal")
Uri videosUri = MediaStore.Video.Media.getContentUri("external");
Log.d(TAG,"videosUri = " + videosUri.toString());
String[] projection = {MediaStore.Video.VideoColumns._ID};
// TODO This will break if we have no matching item in the MediaStore.
Cursor cursor = contentResolver.query(videosUri, projection, MediaStore.Video.VideoColumns.DATA + " LIKE ?", new String[] { filePath }, null);
cursor.moveToFirst();
int columnIndex = cursor.getColumnIndex(projection[0]);
videoId = cursor.getLong(columnIndex);
Log.d(TAG,"Video ID is " + videoId);
cursor.close();
return videoId;
}
В основном, DATA
столбец MediaStore
(или какой-либо его подраздел, к которому вы обращаетесь) хранит путь к файлу, поэтому вы используете эту информацию для его поиска.
// Этот код работает для изображений на 2.2, не уверен, если другие типы носителей
//Your file path - Example here is "/sdcard/cats.jpg"
final String filePathThis = imagePaths.get(position).toString();
MediaScannerConnectionClient mediaScannerClient = new
MediaScannerConnectionClient() {
private MediaScannerConnection msc = null;
{
msc = new MediaScannerConnection(getApplicationContext(), this);
msc.connect();
}
public void onMediaScannerConnected(){
msc.scanFile(filePathThis, null);
}
public void onScanCompleted(String path, Uri uri) {
//This is where you get your content uri
Log.d(TAG, uri.toString());
msc.disconnect();
}
};
Самый простой и надежный способ создания Content Uri content://
из файла использовать FileProvider. Uri, предоставляемый FileProvider, можно использовать также, предоставляя Uri для обмена файлами с другими приложениями. Чтобы получить File Uri с абсолютного пути File
Вы можете использовать DocumentFile.fromFile (новый файл (путь, имя)), он добавлен в Api 22 и возвращает ноль для версий ниже.
File imagePath = new File(Context.getFilesDir(), "images");
File newFile = new File(imagePath, "default_image.jpg");
Uri contentUri = getUriForFile(getContext(), "com.mydomain.fileprovider", newFile);
Вы можете использовать эти два способа в зависимости от использования
Uri uri = Uri.parse("String file location");
или же
Uri uri = Uri.fromFile(new File("string file location"));
Я пробовал оба пути, и оба работают.
Уже поздно, но может помочь кому-то в будущем.
Чтобы получить URI содержимого для файла, вы можете использовать следующий метод:
FileProvider.getUriForFile(Context context, String authority, File file)
Он возвращает URI контента.
Ознакомьтесь с этим, чтобы узнать, как настроить FileProvider
Получение идентификатора файла без написания кода, только с помощью команд консоли командной строки adb:
adb shell content query --uri "content://media/external/video/media" | grep FILE_NAME | grep -Eo " _id=([0-9]+)," | grep -Eo "[0-9]+"
Лучше использовать проверку для поддержки версий до Android N, например:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
imageUri = Uri.parse(filepath);
} else{
imageUri = Uri.fromFile(new File(filepath));
}
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
ImageView.setImageURI(Uri.parse(new File("/sdcard/cats.jpg").toString()));
} else{
ImageView.setImageURI(Uri.fromFile(new File("/sdcard/cats.jpg")));
}
https://es.stackru.com/questions/71443/reporte-crash-android-os-fileuriexposedexception-en-android-n
Вы можете попробовать ниже фрагмент кода
public Uri getUri(ContentResolver cr, String path){
Uri mediaUri = MediaStore.Files.getContentUri(VOLUME_NAME);
Cursor ca = cr.query(mediaUri, new String[] { MediaStore.MediaColumns._ID }, MediaStore.MediaColumns.DATA + "=?", new String[] {path}, null);
if (ca != null && ca.moveToFirst()) {
int id = ca.getInt(ca.getColumnIndex(MediaStore.MediaColumns._ID));
ca.close();
return MediaStore.Files.getContentUri(VOLUME_NAME,id);
}
ca.close();
return null;
}