当前位置: 代码迷 >> 综合 >> 处理Android SDK 29及以上版本,读取不到/storage/emulated/0/(/storage/sdcard/)路径下文件问题
  详细解决方案

处理Android SDK 29及以上版本,读取不到/storage/emulated/0/(/storage/sdcard/)路径下文件问题

热度:98   发布时间:2024-01-13 04:04:31.0

起因:从Android Q开始,出于数据隐私问题,Android 希望禁止应用程序操作非沙箱内的数据(即使你的应用程序获取了读写存储卡权限,也不能读写非沙盒路径下的数据)。但也提供了requestLegacyExternalStorage机制,来帮助应用使用原来的机制继续读写存储卡,此机制用于过度期间的。所以临时解决方法:

       >:  应用程序有存储卡读写权限,且在AndroidManifest.xml的application标签中设置requestLegacyExternalStorage=true,才能访问。

<application...android:requestLegacyExternalStorage="true"...
>

关联问题:

问题1.  Environment.getExternalStorageDirectory() 过期问题(在Android SDK 29及以上废弃)

解决:

// 目标SD路径:/storage/emulated/0
public static String getSDPath(Context context){String sdPath = "";boolean isSDExist = Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED); //判断SD卡是否存在if (isSDExist) {if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {File externalFileRootDir = context.getExternalFilesDir("");do {externalFileRootDir = Objects.requireNonNull(externalFileRootDir).getParentFile();} while (Objects.requireNonNull(externalFileRootDir).getAbsolutePath().contains("/Android"));sdPath = Objects.requireNonNull(externalFileRootDir).getAbsolutePath();} else {sdPath = Environment.getExternalStorageDirectory().getAbsolutePath();}} else {sdPath = Environment.getRootDirectory().toString();//获取跟目录}return sdPath;
}
注意: build.gradle中的'targetSdk'值:'targetSdk 30'时:手机设置里的权限管理中'存储空间 => 访问图片、视频、音频文件',Environment.getExternalStorageDirectory()过期失效,需要使用Context.getExternalFilesDir("")'getExternalFilesDir()'的文件目录为 '/storage/emulated/0/Android/data/包名/files/Media/''targetSdk 29'时:手机设置里的权限管理中'存储空间 => 访问所有类型文件'Environment.getExternalStorageDirectory() 文件目录为 '/storage/emulated/0/'
  相关解决方案