一、前言:
Manifest已經(jīng)配置權(quán)限蛮粮,代碼中也動態(tài)獲取權(quán)限益缎,mkdirs一直返回false,
有的手機android11 或者android12 下載文本到本地文件沒有任何問題然想,但是OPPO(Reno2 Z或者Reno4 Pro)手機創(chuàng)建本地文件夾或者文件一直失敗链峭。
android 11 第一次安裝軟件,F(xiàn)ile.mkdirs()方法創(chuàng)建文件夾失敗
二又沾、解決:
1、動態(tài)申請讀寫權(quán)限
<!--SDCard寫權(quán)限-->
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<!--SDCard讀權(quán)限-->
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<!--在SDCard中創(chuàng)建與刪除文件權(quán)限-->
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS" />
Android XML 添加
2熙卡、在AndroidManifest.xml中添加如下配置:
如果你不想使用Android 10 的新特性來創(chuàng)建文件夾杖刷,那么你可以把targetSdkVersion 改為29之下,因為如果你的應(yīng)用compileSdkVersion為29并且targetSdkVersion為29驳癌,就會使用29的最新源碼編譯和運行滑燃,如果降低targetSdkVersion在系統(tǒng)源碼運行的時候就會找到相應(yīng)的targetSdkVersion版本的源碼,這樣就相當(dāng)于繞過了Android 10新特性颓鲜。
你也可以在Androidmainfest 里面的application添加:
android:requestLegacyExternalStorage="true"
<application
android:name=".base.BWNApplication"
android:allowBackup="true"
android:appComponentFactory="beiwo"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:largeHeap="true"
android:networkSecurityConfig="@xml/network_security_config"
android:requestLegacyExternalStorage="true"
android:resizeableActivity="true"
android:theme="@style/AppTheme"
android:usesCleartextTraffic="true"
tools:ignore="GoogleAppIndexingWarning"
tools:replace="android:appComponentFactory"
android:supportsRtl="true"
tools:targetApi="31">
3表窘、android 11 第一次安裝軟件,F(xiàn)ile.mkdirs()方法創(chuàng)建文件夾失敗
因為第一次安裝軟件后甜滨,F(xiàn)ile.mkdirs()方法創(chuàng)建文件夾失敗乐严,去網(wǎng)上找到了原因在這里
文件路徑原本用的是Environment.getExternalStorageDirectory()
,現(xiàn)在改為context.getFilesDir().getAbsolutePath()
import android.os.Environment;
import java.io.File;
public class SDCardUtil {
/*public static String getInnerSDCardPath() {
return Environment.getExternalStorageDirectory() + File.separator;
}*/
public static String getInnerSDCardPath() {
if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
File external = MainApplication.getContext().getExternalFilesDir(null);
if (external != null) {
return external.getAbsolutePath() + File.separator;
}
}
return MainApplication.getContext().getFilesDir().getAbsolutePath() + File.separator;
}
}
4衣摩、分析文件夾失敗原因:
Manifest已經(jīng)配置權(quán)限昂验,代碼中也動態(tài)獲取權(quán)限,mkdirs一直返回false,
最后找到原因是path的路徑使用的是Environment.getExternalStorageDirectory().getPath()既琴,在compileSdkVersion: 29版本中占婉,該方法標(biāo)注了@Deprecated,里面已經(jīng)說明甫恩,對于Android Q的手機逆济,應(yīng)用程序不再可以直接訪問此方法返回的路徑,所以會一直報錯open failed: ENOENT (No such file or directory)
注意:替換path的路徑方案磺箕,不使用Environment.getExternalStorageDirectory().getPath()即可
private static String getFileRoot(Context context) {
if (Environment.getExternalStorageState().equals(
Environment.MEDIA_MOUNTED)) {
File external = context.getExternalFilesDir(null);
if (external != null) {
return external.getAbsolutePath();
}
}
return context.getFilesDir().getAbsolutePath();
}
參考:https://blog.csdn.net/MoonAndroid/article/details/122824520