`Android Q(Android 10)`之前,需要添加权限,如下:
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/> <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
`Android Q(Android 10)`开始 在`App`专属目录下本`App`可以随意操作,无需申请权限,不过`App`专属目录会在`App`卸载时跟随删除。看下面几个目录(通过`Application`的`context`就可以访问)。
- getFilesDir() :/data/user/0/本应用包名/files
- getCacheDir():/data/user/0/本应用包名/cache
- getExternalFilesDir(null):/storage/emulated/0/Android/data/本应用包名/files
- getExternalCacheDir():/storage/emulated/0/Android/data/本应用包名/cache
`getFilesDir`和`getCacheDir`是在手机自带的一块存储区域(`internal storage`),通常比较小,`SD`卡取出也不会影响到,`App`的`sqlite`数据库和`SharedPreferences`都存储在这里。所以这里应该存放特别私密重要的东西。
`getExternalFilesDir`和`getExternalCacheDir`是在`SD`卡下(`external storage`),在`sdcard/Android/data/包名/files`和`sdcard/Android/data/包名/cache`下,会跟随`App`卸载被删除。
`files`和`cache`下的区别是,在手机设置-找到本应用-在存储中,点击清除缓存,`cache`下的文件会被删除,`files`下的文件不会。
谷歌推荐使用`getExternalFilesDir`。我们项目的下载是个本地功能,下载完成后是存本地数据库的,不是放网络上的,所以下载的音视频都放到了这下面,项目卸载时跟随App都删除了。`getExternalFilesDir`方法需要传入一个参数,传入`null`时得到就是`sdcard/Android/data/包名/files`,传入其他字符串比如"Picture"得到`sdcard/Android/data/包名/files/Picture`。
参考代码如下:
/** * 获取app缓存路径 * * @param context Application Context * @return 缓存路径 */ @NonNull public static String getCacheDir(Context context) { String cacheDir; if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState()) || !Environment.isExternalStorageRemovable()) { //外部存储可用 final File file = context.getExternalCacheDir(); if (null == file) { cacheDir = context.getCacheDir().getPath(); } else { cacheDir = file.getPath(); } } else { //外部存储不可用 cacheDir = context.getCacheDir().getPath(); } return cacheDir; } /** * 获取app文件路径 * * @param context Application Context * @return app文件路径 */ @NonNull public static String getFilesDir(Context context) { String filesDir; if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState()) || !Environment.isExternalStorageRemovable()) { //外部存储可用 final File file = context.getExternalFilesDir(null); if (null == file) { filesDir = context.getFilesDir().getPath(); } else { filesDir = file.getPath(); } } else { //外部存储不可用 filesDir = context.getFilesDir().getPath(); } return filesDir; }