我试图用相机拍照,但我收到以下错误:
FATAL EXCEPTION: main
Process: com.example.marek.myapplication, PID: 6747
java.lang.IllegalArgumentException: Failed to find configured root that contains /storage/emulated/0/Android/data/com.example.marek.myapplication/files/Pictures/JPEG_20170228_175633_470124220.jpg
at android.support.v4.content.FileProvider$SimplePathStrategy.getUriForFile(FileProvider.java:711)
at android.support.v4.content.FileProvider.getUriForFile(FileProvider.java:400)
at com.example.marek.myapplication.MainActivity.dispatchTakePictureIntent(MainActivity.java:56)
at com.example.marek.myapplication.MainActivity.access$100(MainActivity.java:22)
at com.example.marek.myapplication.MainActivity$1.onClick(MainActivity.java:35)
的AndroidManifest.xml:
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="com.example.marek.myapplication.fileprovider"
android:enabled="true"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_paths" />
</provider>
爪哇:
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
// Ensure that there's a camera activity to handle the intent
if (takePictureIntent.resolveActivity(getPackageManager()) != null) {
// Create the File where the photo should go
File photoFile = null;
try {
photoFile = createImageFile();
} catch (IOException ex) {
Toast.makeText(getApplicationContext(), "Error while saving picture.", Toast.LENGTH_LONG).show();
}
// Continue only if the File was successfully created
if (photoFile != null) {
Uri photoURI = FileProvider.getUriForFile(this,
"com.example.marek.myapplication.fileprovider",
photoFile);
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, photoURI);
startActivityForResult(takePictureIntent, REQUEST_TAKE_PHOTO);
}
}
file_paths.xml
<?xml version="1.0" encoding="utf-8"?>
<paths>
<files-path name="my_images" path="images/"/>
</paths>
我整天都在搜索此错误并尝试理解FileProvider
,但我不知道此错误消息试图告诉我什么。如果您想要更多信息/代码,请在评论中写下我。
答案 0 :(得分:93)
您的文件存储在getExternalFilesDir()
下。这映射到<external-files-path>
,而不是<files-path>
。此外,您的文件路径中不包含images/
,因此XML中的path
属性无效。
将res/xml/file_paths.xml
替换为:
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-files-path name="my_images" path="my_images" />
</paths>
答案 1 :(得分:68)
启用flavor(dev,stage)后出现类似问题。
在开始之前,我的路径资源看起来像这样:
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-path
name="my_images"
path="Android/data/pl.myapp/files/Pictures" />
</paths>
添加android:authorities =“$ {applicationId} .fileprovider”之后 在清单appId是pl.myapp.dev或pl.myapp.stage取决于风味和应用程序开始崩溃。 我删除了完整路径并用点替换它,一切都开始工作了。
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-path
name="my_images"
path="." />
</paths>
答案 2 :(得分:43)
这可以解决每个人的问题: 所有标签均已添加,因此您无需担心文件夹路径。 将res / xml / file_paths.xml替换为:
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-path
name="external"
path="." />
<external-files-path
name="external_files"
path="." />
<cache-path
name="cache"
path="." />
<external-cache-path
name="external_cache"
path="." />
<files-path
name="files"
path="." />
</paths>
答案 3 :(得分:40)
如果您使用的是内部缓存,请使用。
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<cache-path name="cache" path="/" />
</paths>
答案 4 :(得分:15)
这让我有点困惑。
问题在于&#34;路径&#34;你的xml文件中的属性。
从此文件中FileProvider &#39;路径&#39;是一个子目录, 但在另一个文件(相机/ photobasics)中显示 &#39;路径&#39;是完整的道路。
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path name="my_images" path="Android/data/com.example.package.name/files/Pictures" />
</paths>
我只是改变了这条路径&#39;完整的道路,它只是工作。
答案 5 :(得分:13)
检查设备提供的存储空间 - 不支持从辅助存储共享文件。查看FileProvider.java
源代码(来自 support-core-utils 25.3.1 ):
} else if (TAG_EXTERNAL_FILES.equals(tag)) {
File[] externalFilesDirs = ContextCompat.getExternalFilesDirs(context, null);
if (externalFilesDirs.length > 0) {
target = externalFilesDirs[0];
}
} else if (TAG_EXTERNAL_CACHE.equals(tag)) {
File[] externalCacheDirs = ContextCompat.getExternalCacheDirs(context);
if (externalCacheDirs.length > 0) {
target = externalCacheDirs[0];
}
}
因此,他们只采用第一个存储空间。
此外,您可以看到getExternalCacheDirs()
用于通过ContextCompat
界面获取存储列表。请参阅documentation了解其限制(例如,它被告知无法识别USB闪存)。最好是自己从这个API中生成一些存储列表的调试输出,这样就可以检查存储路径是否与传递给getUriForFile()
的路径相匹配。
Google的问题跟踪器已经有ticket assigned(06-2017),要求支持多个存储空间。最后,我发现了SO question on this。
答案 6 :(得分:11)
我会迟到但我找到了解决方案。对我来说工作正常,我只是将路径XML文件更改为:
<?xml version="1.0" encoding="utf-8"?>
<paths>
<root-path name="root" path="." />
</paths>
答案 7 :(得分:10)
请注意,external-path并不指向您的辅助存储(即“可移动存储”)(尽管名称为“ external”)。如果出现“无法找到配置的根目录”,则可以将此行添加到XML文件中。
<root-path name="root" path="." />
查看更多详细信息
答案 8 :(得分:8)
我确定我参加晚会很晚,但下面为我工作了。
<paths>
<root-path name="root" path="." />
</paths>
答案 9 :(得分:8)
这些都不适合我。唯一有效的方法是不在xml中声明显式路径。所以这样做并感到高兴:
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path name="my_images" path="." />
</paths>
这里也有一个关于这个问题的优秀教程: https://www.youtube.com/watch?v=9ZxRTKvtfnY&t=613s
答案 10 :(得分:7)
我的问题是我在不同类型的文件路径中有重叠的名称,例如:
<cache-path
name="cached_files"
path="." />
<external-cache-path
name="cached_files"
path="." />
将名称(“ cached_files”)更改为唯一名称后,我摆脱了该错误。我的猜测是这些路径存储在某些HashMap或不允许重复的内容中。
答案 11 :(得分:3)
这也为我工作。我没有给出完整的路径,我给了路径=“图片”,它运作良好。
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-files-path
name="images"
path="Pictures">
</external-files-path>
</paths>
答案 12 :(得分:2)
以上都不对我有用,
经过几个小时的调试,我发现问题出在createImageFile()
,特别是absolute path
与relative path
我认为你们正在使用官方的Android摄影指南。 https://developer.android.com/training/camera/photobasics
private static File createImageFile(Context context) throws IOException {
// Create an image file name
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
String imageFileName = "JPEG_" + timeStamp + "_";
File storageDir = context.getExternalFilesDir(Environment.DIRECTORY_PICTURES);
File image = File.createTempFile(
imageFileName, /* prefix */
".jpg", /* suffix */
storageDir /* directory */
);
// Save a file: path for use with ACTION_VIEW intents
mCurrentPhotoPath = image.getAbsolutePath();
return image;
}
记下storageDir
,这是将在其中创建文件的位置。因此,为了获得该文件的绝对路径,我只使用image.getAbsolutePath()
,如果您在拍照后需要位图图像,则将在onActivityResult
中使用此路径
下面是file_path.xml
,只需使用.
即可使用绝对路径
<paths>
<external-path
name="my_images"
path="." />
</paths>
以及拍照后是否需要位图
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
Bitmap bmp = null;
try {
bmp = BitmapFactory.decodeFile(mCurrentPhotoPath);
} catch (Exception e) {
e.printStackTrace();
}
}
答案 13 :(得分:2)
我为此花了5个小时。
我已经尝试了上述所有方法,但这取决于您的应用程序当前使用的存储空间。
https://developer.android.com/reference/android/support/v4/content/FileProvider#GetUri
在尝试编码之前,请检查文档。
就我而言
因为files-path
子目录将是Context.getFilesDir()
。
有趣的是,Context.getFilesDir()
注意到另一个子目录。
我正在寻找的是
data/user/0/com.psh.mTest/app_imageDir/20181202101432629.png
Context.getFilesDir()
返回
/data/user/0/com.psh.mTest/files
因此标记应为
.... files-path name="app_imageDir" path="../app_imageDir/" ......
然后就可以了!
答案 14 :(得分:2)
我遇到此错误Failed to find configured root that contains...
以下解决方法可以解决我的问题
res / xml / file_paths.xml
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path name="media" path="." />
</paths>
AndroidManifest.xml
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="[PACKAGE_NAME]"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_paths">
</meta-data>
</provider>
ActivityClass.java
void shareImage() {
Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("image/*");
intent.putExtra(Intent.EXTRA_STREAM, FileProvider.getUriForFile(this,"com.slappstudio.pencilsketchphotomaker", selectedFilePath));
startActivity(Intent.createChooser(intent,getString(R.string.string_share_with)));
}
答案 15 :(得分:2)
我做了什么来解决这个问题 -
的AndroidManifest.xml
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="com.mydomain.fileprovider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/filepaths"/>
</provider>
filepaths.xml(允许FileProvider共享应用程序外部文件目录中的所有文件)
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-files-path name="files"
path="/" />
</paths>
和java类 -
Uri fileProvider = FileProvider.getUriForFile(getContext(),"com.mydomain.fileprovider",newFile);
答案 16 :(得分:2)
过去2周,试图找到一些解决方案...如果您尝试以上所有方法后到达这里:
1-验证标签提供者是否在标签应用程序内部
<application>
<provider android:name="android.support.v4.content.FileProvider" android:authorities="com.companyname.Pocidadao.fileprovider" android:exported="false" android:grantUriPermissions="true">
<meta-data android:name="android.support.FILE_PROVIDER_PATHS" android:resource="@xml/file_paths"></meta-data>
</provider>
</application>
2-如果您尝试许多尝试均未成功,请使用以下方法进行测试:
<?xml version="1.0" encoding="utf-8"?>
<paths>
<cache-path name="cache" path="." />
<external-path name="external" path="." />
<root-path name="root" path="." />
<files-path name="my_images" path="/" />
<files-path name="my_images" path="myfile/"/>
<files-path name="files" path="." />
<external-path name="external_files" path="." />
<external-path name="images" path="Pictures" />
<external-path name="my_images" path="." />
<external-path name="my_images" path="Android/data/com.companyname.yourproject/files/Pictures" />
<external-path name="my_images" path="Android/data/com.companyname.yourproject/files/Pictures/" />
<external-files-path name="images" path="Pictures"/>
<external-files-path name="camera_image" path="Pictures/"/>
<external-files-path name="external_files" path="." />
<external-files-path name="my_images" path="my_images" />
<external-cache-path name="external_cache" path="." />
</paths>
对此进行测试,如果相机可以正常工作,则开始消除一些线条并继续测试...
3-别忘了验证相机是否在模拟器中处于活动状态。
答案 17 :(得分:1)
如果您的文件路径类似于/ storage / emulated / 0 /“ yourfile”
您只需要修改FileProvider xml
<paths>
<external-path name="external" path="." />
</paths>
然后在需要共享文件时调用此功能
Intent sharingIntent = new Intent(Intent.ACTION_SEND);
Uri fileUri = FileProvider.getUriForFile(getContext(),
"com.example.myapp.fileprovider",
file);
sharingIntent.setType("*/*"); // any flie type
sharingIntent.putExtra(Intent.EXTRA_STREAM, fileUri);
startActivity(Intent.createChooser(sharingIntent, "Share file"));
它适用于android M〜Pie
答案 18 :(得分:1)
这取决于您要进行哪种存储,内部存储还是外部存储
用于外部存储
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-files-path name="my_images" path="my_images" />
</paths>
但是对于内部存储,请谨慎使用路径,因为它使用getFilesDir()方法 这意味着您的文件将位于应用程序的根目录(“ /”)
File storeDir = getFilesDir(); // path "/"
因此您的提供程序文件必须是这样的:
<paths>
<files-path name="my_images" path="/" />
</paths>
答案 19 :(得分:1)
xml file_paths文件中的以下更改对我有用。
<external-files-path name="my_images" path="Pictures"/>
<external-files-path name="my_movies" path="Movies"/>
答案 20 :(得分:1)
Android官方文档说file_paths.xml应该有:
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path name="my_images"
path="Android/data/com.example.package.name/files/Pictures" />
</paths>
但要使它在最新的android中工作,路径的末尾应该有一个“/”,如下所示:
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path name="my_images"
path="Android/data/com.example.package.name/files/Pictures/" />
</paths>
答案 21 :(得分:0)
你好朋友,请尝试
在此代码中
1)如何在清单中声明2个文件提供程序。
2)第一个文件下载提供商
3)第二个提供者用于摄像头和画廊
STEP 1
www.example.com
Provider_paths.xml
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="${applicationId}.fileprovider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths" />
</provider>
第二提供商
<?xml version="1.0" encoding="utf-8"?>
<paths>
<files-path name="apks" path="." />
</paths>
file_path.xml
<provider
android:name=".Utils.MyFileProvider"
android:authorities="${applicationId}.provider"
android:exported="false"
android:grantUriPermissions="true"
tools:replace="android:authorities"
tools:ignore="InnerclassSeparator">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_path" />
</provider>
.Utils.MyFileProvider
创建类 MyFileProvider (仅创建类,没有任何方法声明)
使用文件提供程序时使用(.fileprovider)此名称,而用于图像(.provider)中使用此名称。
如果有任何人需要理解此代码,您可以通过rp1741995@gmail.com与我联系。我会为您提供帮助。
答案 22 :(得分:0)
如果没有任何帮助,而您却得到了错误
failed to find configured root that contains /data/data/...
然后尝试更改某些行,例如:
File directory = thisActivity.getDir("images", Context.MODE_PRIVATE);
收件人:
File directory = new File(thisActivity.getFilesDir(), "images");
并在xml文件中:
<files-path name="files" path="." />
这很奇怪,因为我访问的文件夹是/images
。
答案 23 :(得分:0)
我遇到了同样的问题,我尝试使用以下代码进行工作。
1.Create Xmlfile:provider_paths
<?xml version="1.0" encoding="utf-8"?>
<paths>
<files-path name="my_images" path="myfile/"/>
</paths>
<强> 2。主要文件
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="com.ril.learnet.provider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths"/>
</provider>
3.在您的Java文件中。
File file = new File(getActivity().getFilesDir(), "myfile");
if (!file.exists()) {
file.mkdirs();
}
String destPath = file.getPath() + File.separator + attachmentsListBean.getFileName();
file mfile = new File(destPath);
Uri path;
Intent intent = new Intent(Intent.ACTION_VIEW);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
{
path = FileProvider.getUriForFile(AppController.getInstance().getApplicationContext(), AppController.getInstance().getApplicationContext().getPackageName() + ".provider", mfile );
intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
} else {
path = Uri.fromFile(mfile);
}
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setDataAndType(path, "image/*");
getActivity().startActivity(intent);
答案 24 :(得分:0)
我注意到有关path.xml
文件的政策或行为在支持库26和27之间发生了变化。为了从相机中捕获图片,我看到了以下更改:
26岁时,我不得不使用<external-path>
和path
参数中给出的完整路径。
使用27,我必须使用<external-files-path>
并且只使用path
参数中的子文件夹。
因此,path.xml
文件是支持库27的具体工作原理是
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-files-path name="camera_image" path="Pictures/"/>
</paths>
答案 25 :(得分:0)
问题可能不只是路径xml。
以下是我的解决方法:
查看let newURL = outputURL.deletingPathExtension().appendingPathExtension("mp3")
try FileManager.default.moveItem(at: outputURL, to: newURL)
中的根课程:
android.support.v4.content.FileProvider$SimplePathStrategy.getUriForFile()
这意味着 public File getFileForUri(Uri uri) {
String path = uri.getEncodedPath();
final int splitIndex = path.indexOf('/', 1);
final String tag = Uri.decode(path.substring(1, splitIndex));
path = Uri.decode(path.substring(splitIndex + 1));
final File root = mRoots.get(tag); // mRoots is parsed from path xml
if (root == null) {
throw new IllegalArgumentException("Unable to find configured root for " + uri);
}
// ...
}
应该包含所请求uri的标签。 所以我写了一些代码来打印mRoots
和uri标签,然后轻松地找到标签不匹配。
结果是,将提供者权限设置为mRoots
是一个愚蠢的想法!这种授权是如此普遍,以至于其他提供者可能会使用它,这会弄乱路径配置!
答案 26 :(得分:0)
您需要从以下位置更改xml文件file_paths.xml
<?xml version="1.0" encoding="utf-8"?>
<paths>
<files-path name="my_images" path="images/"/>
</paths>
到
<?xml version="1.0" encoding="utf-8"?>
<paths>
<fexeternal-path name="my_images" path="Android/data/com.example.marek.myapplication/files/Pictures"/>
</paths>
答案 27 :(得分:0)
这也可能是因为在定位Android 7.1,8.0 +时未更新您的支持包。将它们更新为v25.4.0.2+并且此特定错误可能会消失(假设您已按照其他人的说明正确配置了file_path文件)。
给出背景信息:我转而从 Nougat 中定位 Oreo Xamarin.Forms应用并使用Xam.Plugin.Media拍照 开始失败并出现上述错误消息,因此更新包 为我做了诀窍。
答案 28 :(得分:0)
我的问题文件名错误:
我在清单中将资源设置为file_paths.xml
时,在res / xml下创建了provider_paths.xml
:
<provider
android:authorities="ir.aghigh.radio.fileprovider"
android:name="android.support.v4.content.FileProvider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths"/>
</provider>
我将provider_paths
更改为file_paths
并解决了问题。
答案 29 :(得分:0)
您需要确保file_paths.xml文件的内容包含以下字符串=>“ /Android/data/com.example.marek.myapplication/files/Pictures /”
从错误消息开始,即存储图片的路径。查看预期的样本
files_path.xml如下:
<external-path name="qit_images" path="Android/data/com.example.marek.myapplication/files/Pictures/" />
答案 30 :(得分:0)
我看到至少你没有提供与file_paths.xml中的其他路径相同的路径。 因此,请确保在3个地方提供完全相同的包裹名称或路径,包括:
android:authorities
属性path
属性
调用FileProvider.getUriForFile()时的authority
参数。答案 31 :(得分:0)
@ CommonsWare 的答案很好。
但就我而言,我必须添加多个路径。
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-path name="external_files" path="." />
<files-path name="external_files" path="." />
</paths>
答案 32 :(得分:-5)
试试这个
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path
name="my_images"
path="" />
</paths>