Я пытаюсь исправить проблему после добавления новой функции в файловую систему Android, но получаю следующую ошибку:
android.os.FileUriExposedException: file:///storage/emulated/0/MyApp/Camera_20180105_172234.jpg exposed beyond app through ClipData.Item.getUri()
Так что я надеюсь, что кто-нибудь поможет мне это исправить :)
Благодарность
private Uri getTempUri() {
// Create an image file name
SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMdd_HHmmss");
String dt = sdf.format(new Date());
imageFile = null;
imageFile = new File(Environment.getExternalStorageDirectory()
+ "/MyApp/", "Camera_" + dt + ".jpg");
AppLog.Log(
TAG,
"New Camera Image Path:- "
+ Environment.getExternalStorageDirectory()
+ "/MyApp/" + "Camera_" + dt + ".jpg");
File file = new File(Environment.getExternalStorageDirectory() + "/MyApp");
if (!file.exists()) {
file.mkdir();
}
imagePath = Environment.getExternalStorageDirectory() + "/MyApp/"
+ "Camera_" + dt + ".jpg";
imageUri = Uri.fromFile(imageFile);
return imageUri;
}
Ответы:
Для sdk 24 и выше, если вам нужно получить Uri файла за пределами вашего хранилища приложения, у вас есть эта ошибка.
Решения @ eranda.del позволяют вам изменить политику, чтобы разрешить это, и это работает нормально.
Однако, если вы хотите следовать руководству Google без изменения политики API вашего приложения, вам необходимо использовать FileProvider.
Сначала, чтобы получить URI файла, вам нужно использовать метод FileProvider.getUriForFile ():
Uri imageUri = FileProvider.getUriForFile( MainActivity.this, "com.example.homefolder.example.provider", //(use your app signature + ".provider" ) imageFile);
Затем вам нужно настроить своего провайдера в манифесте Android:
<application> ... <provider android:name="android.support.v4.content.FileProvider" android:authorities="com.example.homefolder.example.provider" android:exported="false" android:grantUriPermissions="true"> <!-- ressource file to create --> <meta-data android:name="android.support.FILE_PROVIDER_PATHS" android:resource="@xml/file_paths"> </meta-data> </provider> </application>
(В разделе «Авторитет» используйте то же значение, что и второй аргумент метода getUriForFile () (подпись приложения + «.provider»))
И, наконец, вам нужно создать файл ресурсов: "file_paths". Этот файл необходимо создать в каталоге res / xml (вероятно, вам также потребуется создать этот каталог):
<?xml version="1.0" encoding="utf-8"?> <paths xmlns:android="http://schemas.android.com/apk/res/android"> <external-path name="external_files" path="." /> </paths>
источник
<external-path ...
используется, когда вам нужен Environment.getExternalStorageDirectory (). и используйте,<files-path ...
если вам нужен Context.getFilesDir (). Вам лучше сначала проверить официальную документацию: developer.android.com/reference/android/support/v4/content/…androidx
нем:android:name="androidx.core.content.FileProvider"
Добавьте следующий блок кода перед запуском камеры или просмотра файлов
StrictMode.VmPolicy.Builder builder = new StrictMode.VmPolicy.Builder(); StrictMode.setVmPolicy(builder.build());
Пожалуйста, обратитесь к строгому режиму реферальной ссылки и объясните все способы использования и технические детали.
источник
Нет обязательной конфигурации поставщика в AndroidManifest, только разрешение на камеру и хранилище. Используйте следующий код для запуска камеры:
final int REQUEST_ACTION_CAMERA = 9; void openCamra() { Intent cameraImgIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE); cameraImgIntent.putExtra(MediaStore.EXTRA_OUTPUT, FileProvider.getUriForFile(this, BuildConfig.APPLICATION_ID +".provider", new File("your_file_name_with_dir"))); startActivityForResult(cameraImgIntent, REQUEST_ACTION_CAMERA); }
После захвата изображения вы можете найти его в:
"your_file_name_with_dir"
источник
добавить код в
onCreate(Budle savedInstancesState){ if (Build.VERSION.SDK_INT >= 24) { try { Method m = StrictMode.class.getMethod("disableDeathOnFileUriExposure"); m.invoke(null); } catch (Exception e) { e.printStackTrace(); } }
источник