NotificationSetUtilDemo【判断APP通知栏权限是否开启,以及如何跳转到应用程序设置界面】
前言
当APP有推送功能时,需要判断当前app在手机中是否开启了允许消息推送,否则即使添加了推送代码仍然收不到通知。
效果图
oppo上的效果:
使用步骤
一、项目组织结构图
注意事项:
1、 导入类文件后需要change包名以及重新import R文件路径
2、 Values目录下的文件(strings.xml、dimens.xml、colors.xml等),如果项目中存在,则复制里面的内容,不要整个覆盖
二、导入步骤
1、将NotificationSetUtil.java类复制到项目中
package com.why.project.notificationsetutildemo.utils; import android.app.AppOpsManager;
import android.content.Context;
import android.content.Intent;
import android.content.pm.ApplicationInfo;
import android.net.Uri;
import android.os.Build;
import android.support.annotation.RequiresApi;
import android.support.v4.app.NotificationManagerCompat; import java.lang.reflect.Field;
import java.lang.reflect.Method; /**
* Created by HaiyuKing
* Used 判断是否开启消息通知,没有开启的话跳转到手机系统设置界面
* 参考:https://blog.csdn.net/lidayingyy/article/details/81778894
* https://www.jianshu.com/p/205bc87cac29
* https://blog.csdn.net/yrmao9893/article/details/74607402/
* https://www.meiwen.com.cn/subject/qcklpftx.html
*/
public class NotificationSetUtil { //判断是否需要打开设置界面
@RequiresApi(api = Build.VERSION_CODES.KITKAT)
public static void OpenNotificationSetting(Context context, OnNextLitener mOnNextLitener) {
if (!isNotificationEnabled(context)) {
gotoSet(context);
} else {
if (mOnNextLitener != null) {
mOnNextLitener.onNext();
}
}
} //判断该app是否打开了通知
/**
* 可以通过NotificationManagerCompat 中的 areNotificationsEnabled()来判断是否开启通知权限。NotificationManagerCompat 在 android.support.v4.app包中,是API 22.1.0 中加入的。而 areNotificationsEnabled()则是在 API 24.1.0之后加入的。
* areNotificationsEnabled 只对 API 19 及以上版本有效,低于API 19 会一直返回true
* */
@RequiresApi(api = Build.VERSION_CODES.KITKAT)
public static boolean isNotificationEnabled(Context context) {
if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT){
NotificationManagerCompat notificationManagerCompat = NotificationManagerCompat.from(context);
boolean areNotificationsEnabled = notificationManagerCompat.areNotificationsEnabled();
return areNotificationsEnabled;
} String CHECK_OP_NO_THROW = "checkOpNoThrow";
String OP_POST_NOTIFICATION = "OP_POST_NOTIFICATION"; AppOpsManager mAppOps = (AppOpsManager) context.getSystemService(Context.APP_OPS_SERVICE);
ApplicationInfo appInfo = context.getApplicationInfo();
String pkg = context.getApplicationContext().getPackageName();
int uid = appInfo.uid; Class appOpsClass = null;
/* Context.APP_OPS_MANAGER */
try {
appOpsClass = Class.forName(AppOpsManager.class.getName());
Method checkOpNoThrowMethod = appOpsClass.getMethod(CHECK_OP_NO_THROW, Integer.TYPE, Integer.TYPE,
String.class);
Field opPostNotificationValue = appOpsClass.getDeclaredField(OP_POST_NOTIFICATION); int value = (Integer) opPostNotificationValue.get(Integer.class);
return ((Integer) checkOpNoThrowMethod.invoke(mAppOps, value, uid, pkg) == AppOpsManager.MODE_ALLOWED); } catch (Exception e) {
e.printStackTrace();
}
return false; } //打开手机设置页面
/**
* 假设没有开启通知权限,点击之后就需要跳转到 APP的通知设置界面,对应的Action是:Settings.ACTION_APP_NOTIFICATION_SETTINGS, 这个Action是 API 26 后增加的
* 如果在部分手机中无法精确的跳转到 APP对应的通知设置界面,那么我们就考虑直接跳转到 APP信息界面,对应的Action是:Settings.ACTION_APPLICATION_DETAILS_SETTINGS*/
private static void gotoSet(Context context) { Intent intent = new Intent();
if (Build.VERSION.SDK_INT >= 26) {
// android 8.0引导
intent.setAction("android.settings.APP_NOTIFICATION_SETTINGS");
intent.putExtra("android.provider.extra.APP_PACKAGE", context.getPackageName());
} else if (Build.VERSION.SDK_INT >= 21) {
// android 5.0-7.0
intent.setAction("android.settings.APP_NOTIFICATION_SETTINGS");
intent.putExtra("app_package", context.getPackageName());
intent.putExtra("app_uid", context.getApplicationInfo().uid);
} else {
// 其他
intent.setAction("android.settings.APPLICATION_DETAILS_SETTINGS");
intent.setData(Uri.fromParts("package", context.getPackageName(), null));
}
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(intent);
} /*=====================添加Listener回调================================*/
public interface OnNextLitener {
/**
* 不需要设置通知的下一步
*/
void onNext();
} private OnNextLitener mOnNextLitener; public void setOnNextLitener(OnNextLitener mOnNextLitener) {
this.mOnNextLitener = mOnNextLitener;
}
}
NotificationSetUtil.java
三、使用方法
package com.why.project.notificationsetutildemo; import android.content.Context;
import android.os.Build;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.widget.Toast; import com.why.project.notificationsetutildemo.utils.NotificationSetUtil; public class MainActivity extends AppCompatActivity { private Context mContext; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); mContext = this; if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
//判断是否需要开启通知栏功能
NotificationSetUtil.OpenNotificationSetting(mContext, new NotificationSetUtil.OnNextLitener() {
@Override
public void onNext() {
Toast.makeText(mContext,"已开启通知权限",Toast.LENGTH_SHORT).show();
}
});
}
}
}
混淆配置
无
参考资料
Android 判断应用程序获取通知栏权限是否开启,以及如何跳转到应用程序设置界面
项目demo下载地址
暂不需要
NotificationSetUtilDemo【判断APP通知栏权限是否开启,以及如何跳转到应用程序设置界面】的更多相关文章
- iOS用户是否打开APP通知开关跳转到系统的设置界面
1.检测用户是否打开推送通知 /** 系统通知是否打开 @return 是否打开 */ //检测通知是否打开iOS8以后有所变化 所以需要适配iOS7 + (BOOL)openThePushNoti ...
- (转载)安卓6.0之前的系统 判断app是否有录音权限
卓6.0之前的系统 判断app是否有录音权限 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 ...
- iOS 权限判断 跳转对应设置界面
相机权限 1.1 使用说明 在合适的地方导入#import <AVFoundation/AVFoundation.h> 使用AVAuthorizationStatus类获取当前权限状态 在 ...
- Android ROM开发(三)——精简官方ROM并且内置ROOT权限,开启Romer之路
Android ROM开发(三)--精简官方ROM并且内置ROOT权限,开启Romer之路 相信ROM的相关信息大家通过前几篇的学习都是有所了解了,这里就不在一一提示了,这里我们下载一个官方包,我们还 ...
- 4.功能三:实现URL地址栏控制(15分) (1)获取到当前访问的控制器和方法(5分) (2)对当前访问的控制器和方法进行判断,有权限继续访问(5分) (3)无权限给出提示(5分)
<?php namespace app\admin\controller; use think\Controller; use think\Request; class Base extends ...
- java中 用telnet 判断服务器远程端口是否开启
package net.jweb.common.util; import java.io.BufferedReader; import java.io.BufferedWriter; import j ...
- 判断App运行是否在前台
转自:http://notes.stay4it.com/2016/02/26/check-if-app-is-running-forground/ 在一些场景中,经常会需要判断App是否在后台运行,比 ...
- 判断App是否在后台运行
在一些场景中,经常会需要判断App是否在后台运行,比如是否显示解锁界面,收到新消息是否显示Notification等.需求可能是多样化的,但所依仗的原理是相通的,今天Stay打算说说这些需求的最优解. ...
- Android判断App是否在前台运行(转)
原文地址: http://blog.csdn.net/zuolongsnail/article/details/8168689 Android开发中,有时候需要判断App是否在前台运行. 代码实现如下 ...
随机推荐
- Python 作用域, 局部与全局变量
全局与局部变量 在子程序(函数)中定义的变量称为局部变量, 在程序的一开始定义的变量称为全局变量 全局变量作用于整个程序, 局部变量作用域是定义该变量的子程序 当全局变量与局部变量重名时: 在定义局部 ...
- 连续查询(Continuous Queries)
当数据超过保存策略里指定的时间之后,就会被删除.如果我们不想完全删除掉,比如做一个数据统计采样:把原先每秒的数据,存为每小时的数据,让数据占用的空间大大减少(以降低精度为代价). 这就需要Influx ...
- luoguP4231_三步必杀_差分
luoguP4231_三步必杀_差分 题意:N 个柱子排成一排,一开始每个柱子损伤度为0.接下来勇仪会进行M 次攻击,每次攻击可以用4个参数l,r ,s ,e 来描述: 表示这次攻击作用范围为第l个到 ...
- BZOJ_4517_[Sdoi2016]排列计数_组合数学
BZOJ_4517_[Sdoi2016]排列计数_组合数学 Description 求有多少种长度为 n 的序列 A,满足以下条件: 1 ~ n 这 n 个数在序列中各出现了一次 若第 i 个数 A[ ...
- RocketMQ源码 — 十一、 RocketMQ事务消息
分布式事务是一个复杂的问题,rmq实现了事务的最终一致性,rmq保证本地事务成功消息一定会发送成功并被成功消费,如果本地事务失败了,消息不会被发送. rmq事务消息的实现过程为: producer发送 ...
- Vue 进阶之路(九)
之前的文章我们介绍了 vue 中父组件之间的传值,本章我们再来看一下父子组件间传值的参数校验和非 Props 特性. <!DOCTYPE html> <html lang=" ...
- 网页的cdn引用地址,js,react,bootstrap
react+----这三个够用了 <script src="https://cdn.bootcss.com/react/15.4.2/react.min.js">< ...
- Actor模型及原理
1.Actor模型 在使用Java进行并发编程时需要特别的关注锁和内存原子性等一系列线程问题,而Actor模型内部的状态由它自己维护即它内部数据只能由它自己修改(通过消息传递来进行状态修改),所以使用 ...
- 使用Scala IDE for Eclipse遇到build errors错误的解决办法
在编写第一个Scala语言的Spark程序时,在Scala IDE for Eclipse中运行程序时出现“Project XXXX contains build errors, Continue l ...
- 从壹开始微服务 [ DDD ] 之十二 ║ 核心篇【下】:事件驱动EDA 详解
缘起 哈喽大家好,又是周二了,时间很快,我的第二个系列DDD领域驱动设计讲解已经接近尾声了,除了今天的时间驱动EDA(也有可能是两篇),然后就是下一篇的事件回溯,就剩下最后的权限验证了,然后就完结了, ...