Android 8.0+ 通知栏兼容问题
当build.gradle里的targetSdk=23时(各大应用市场陆续提出此需求),之前app更新时使用的通知栏处理的代码出现了兼容性问题,Android O以后通知栏必须设置channelId,如果你把targetSdk设为23,之前的创建Notification.Builder代码会提示过时 new NotificationCompat.Builder(this),需要使用new NotificationCompat.Builder(this, channelId)来创建
private void createNotification() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
String channelId = "channel_update";
String channelName = "更新apk";
mBuilder = new NotificationCompat.Builder(this, channelId);
int importance = NotificationManager.IMPORTANCE_LOW;
NotificationChannel channel = new NotificationChannel(channelId, channelName, importance);
mNotifyManager.createNotificationChannel(channel);
mBuilder.setSmallIcon(R.mipmap.notify_icon);
} else {
mBuilder = new NotificationCompat.Builder(this);
if (Build.VERSION.SDK_INT > Build.VERSION_CODES.LOLLIPOP) {
mBuilder.setSmallIcon(R.mipmap.notify_icon);
} else {
mBuilder.setSmallIcon(R.mipmap.app_icon_new);
}
}
if (getApplicationInfo().labelRes != 0) {
String appName = getString(getApplicationInfo().labelRes);
mBuilder.setContentTitle(appName);
} else {
mBuilder.setContentTitle("xxxx");
}
}
而且在5.0以后谷歌要求对通知栏的图标做处理,所以如果你发现你的通知栏图标变成了白色小方块,不要慌,求助UI帮你切一张图,要求就是:背景色透明,然后用白色画图案
下载更新完成后 install APK 的时候又会有兼容问题,因为android 7以后需要使用FileProvider,代码如下:
/**
* 安装APK文件
*/
private void installApk(File file) {
if (file == null || !file.getPath().endsWith(".apk")) {
return;
}
Intent intent = new Intent(Intent.ACTION_VIEW);
if (Build.VERSION.SDK_INT >= 24) {
Uri apkUri = FileProvider.getUriForFile(this, "yourAppId.provider", file);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
intent.setDataAndType(apkUri, "application/vnd.android.package-archive");
} else {
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setDataAndType(Uri.fromFile(file), "application/vnd.android.package-archive");
}
startActivity(intent);
//强制更新时,安装应用程序前退出应用,这里最好是加上一点延迟,防止获取不到FileProvider,可以使用Handler或者RxJava
if (bForceUpdate) {
//设置延迟,防止退出应用前未获取FileProvider
mDisposable = Observable.timer(500, TimeUnit.MILLISECONDS).observeOn(AndroidSchedulers.mainThread())
.subscribeOn(Schedulers.io()).subscribe(new Consumer<Long>() {
@Override
public void accept(Long aLong) throws Exception {
EventBus.getDefault().post(new ForceExitBean());
}
});
}
}
同时不要忘记了要在AndroidManifest里面配置你的provider:
<!-- ### provider start ### -->
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="${applicationId}.provider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/你的自定义命名" />
</provider>
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-path name="external_storage_root" path="."/>
</paths>
网友评论