/**
*
* app文件分为专属文件和独立文件;
* 手机存储分内部存储(手机存储,如4G,8G内存) 和外部存储(SD拓展卡,如64G,128G)
* 专属文件是那些只有该app才可以使用的文件,例如数据库,sharedpreference,专属格式的电子书等;专属文件可存于内部和外部存储;专属文件会随APP卸载而删除.
* 独立文件是那些不依赖于某特定app的文件,例如照片,视频,apk等;独立文件可存于内部和外部存储;独立文件不应该随APP卸载而卸载.
*
* 在安卓10.0之后不建议使用Environment.getExternalStorageDirectory()方法1,推荐使用context.getExternalFilesDir()方法2;
* 10.0后方法1能访问,但是无法创建自定义的文件夹;方法2创建的文件夹都是在/storage/emulated/0/Android/data/packageName/files下,会随应用卸载被删除;
* 想要在外部存储创建自定义文件夹就只能把targetSDK设置到28及以下,并使用方法1获取目录并创建自定义文件夹.
*
* 此方法测试时,targetSDK=27
*/
private void testDirector() {
final String privilegePath1 = Utils.getContext().getFilesDir().getAbsolutePath();
final String privilegePath2 = Utils.getContext().getExternalFilesDir(null).getAbsolutePath();
final String privilegePath3 = Utils.getContext().getExternalFilesDir(Environment.DIRECTORY_DOWNLOADS).getAbsolutePath();
final String privilegePath4 = Utils.getContext().getExternalFilesDir(Environment.DIRECTORY_DOCUMENTS).getAbsolutePath();
final String privilegePath5 = Environment.getExternalStorageState();
final String privilegePath6 = Environment.getRootDirectory().getAbsolutePath();
final String privilegePath7 = Environment.getDataDirectory().getAbsolutePath();
final String privilegePath8 = Environment.getDownloadCacheDirectory().getAbsolutePath();
final String privilegePath9 = Environment.getStorageDirectory().getAbsolutePath();
final String privilegePath10 = Environment.getExternalStorageDirectory().getAbsolutePath();
final String privilegePath11 = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES).getAbsolutePath();
final String privilegePath12 = Environment.getStorageState(null);
LogUtil.logInfo("aaa",
"path1=" + privilegePath1 + ";" +
"path2=" + privilegePath2 + ";" +
"path3=" + privilegePath3 + ";" +
"path4=" + privilegePath4 + ";" +
"path5=" + privilegePath5 + ";" +
"path6=" + privilegePath6 + ";" +
"path7=" + privilegePath7 + ";" +
"path8=" + privilegePath8 + ";" +
"path9=" + privilegePath9 + ";" +
"path10=" + privilegePath10 + ";" +
"path11=" + privilegePath11 + ";" +
"path12=" + privilegePath12 + ";" +
"pathAppCache=" + Constant.APP_CACHE_ROOT_PATH);
/**
* 打印结果
* path1=/data/user/0/com.yuwj.modulepatternjwt/files;
* path2=/storage/emulated/0/Android/data/com.yuwj.modulepatternjwt/files;
* path3=/storage/emulated/0/Android/data/com.yuwj.modulepatternjwt/files/Download;
* path5=mounted;
* path6=/system;
* path7=/data;
* path8=/data/cache;
* path9=/storage;
* path10=/storage/emulated/0;
* path12=unknown;
* pathAppCache=/data/user/0/com.yuwj.modulepatternjwt/files/ModulePatternJWT/
*/
}
==================================================
==================================================
==================================================
/**
* fileprovider的使用方法,参见https://www.jianshu.com/p/bce6a4c779dd
* 1. 在manifest的application中定义provider
* 2. 创建对应的xml/filepath.xml文件,编辑内容
* 3. 在读取文件时,需要将文件的绝对路径转化为FileProvider提供的URI.
* 4. filepath.xml说明
* <root-path/> 代表设备的根目录new File("/");
* <files-path/> 代表context.getFilesDir()
* <cache-path/> 代表context.getCacheDir()
* <external-path/> 代表Environment.getExternalStorageDirectory()
* <external-files-path>代表context.getExternalFilesDirs()
* <external-cache-path>代表getExternalCacheDirs()
* path表示相对于<external-files-path>的子目录
* name表示将代替<external-files-path>+path对应的目录,使调用者不清楚实际文件路径
*/
<provider
android:name="androidx.core.content.FileProvider"
android:authorities="${applicationId}.fileprovider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/filepath" />
</provider>
============================1=============================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<paths>
<external-files-path
name="files"
path="" />
</paths>
</resources>
============================2=============================
public static void installApk(Context context, String apkPath) {
File file = new File(apkPath);
boolean i = file.exists();
if(Build.VERSION.SDK_INT>=24) {//判读版本是否在7.0以上
//参数1 上下文, 参数2 Provider主机地址 和配置文件中保持一致 参数3 共享的文件
Uri apkUri = FileProvider.getUriForFile(context, context.getPackageName()+".provider", file);//在AndroidManifest中的android:authorities值
Intent install = new Intent(Intent.ACTION_VIEW);
// 由于没有在Activity环境下启动Activity,设置下面的标签
install.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
//添加这一句表示对目标应用临时授权该Uri所代表的文件
install.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
install.setDataAndType(apkUri, "application/vnd.android.package-archive");
context.startActivity(install);
} else{
Intent install = new Intent(Intent.ACTION_VIEW);
install.setDataAndType(Uri.fromFile(file), "application/vnd.android.package-archive");
install.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(install);
}
}
============================3=============================