在Android手机上,基本上每天都能看到各种各样的推送,如网易云的推荐,新闻的推荐,QQ,WeChat的消息推送,那通知又是怎样发送过来的呢?
Notification
通知的基本流程
- 创建通知
通知是通过Notification.Builder.build()来完成创建的 - 发送通知
通知创建完,然后委托NotificationManager.notify()进行发送
创建通知须知
创建通知的时候,必须给通知设定如下内容
- 通知的小图标:setSmallIcon()
- 通知的标题:setContentTitle()
- 通知的内容:setContentText()
按照第一行代码创建出来的通知会出现这样的报错
然后我上网搜索了一下:Android O的更新使得在Android版本8.0以上的机器发送通知都要设定一个ChannelId,否则就会跳出上图所示的Toast
然后打开Notificaition.Builder(Context)的构造器,发现已被标识deprecated,且推荐我们使用
Notification.Builder(Context, String)的构造器,多出的那个String属性就是ChannelId
/**
* @deprecated use {@link Notification.Builder#Notification.Builder(Context, String)}
* instead. All posted Notifications must specify a NotificationChannel Id.
*/
@Deprecated
public Builder(Context context) {
this(context, (Notification) null);
}
改进代码后,Notification顺利的弹出来了~
public class NotifyActivity extends AppCompatActivity {
NotificationManager manager;
NotificationCompat.Builder builder;
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_notify);
manager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
builder = new NotificationCompat.Builder(this, "ChannelId");
manager.createNotificationChannel(new NotificationChannel("ChannelId", "订阅消息推送", NotificationManager.IMPORTANCE_DEFAULT));
} else {
builder = new NotificationCompat.Builder(this);
}
builder.setSmallIcon(R.drawable.ic_launcher_background)
.setContentText("text")
.setContentTitle("title");
findViewById(R.id.btn_notify).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (manager != null) {
manager.notify(1, builder.build());
}
}
});
}
}
8.0特性 Tips:
Notification.Builder(Context context, String id)和NotificationChannel(String id, CharSequence name, @Importance int importance)要保持id的一致性,不然也会报错
-
然后NotificationChannel中的name属性是来描述这条通知的类型的
用户可以到应用设置-通知,来选择是否展示某一类的通知
如下图,这里我们可以自由开关id为ChannelId,name为订阅消息推送的推送开关
具体可以查看郭霖大大的博客Android 8.0通知栏技巧
现在我们的通知只是有了内容,但是点击该通知却毫无反应,这会造成不好的用户体验
实现通知的点击效果需要靠PendingIntent
它和Intent很类似,通俗的说
Intent是个急性子,有想法了就马上就做
PendingIntent则更有规划,它会在合适的时候去做
protected void onCreate(Bundle savedInstanceState) {
//其他代码...
PendingIntent pi = PendingIntent.getActivity(this,0,new Intent(this, MainActivity.class),0);
builder.setContentIntent(pi);
}
按照上述代码,点击通知后会跳转到MainActivity中,但此时通知栏的通知仍然照常显示,按照我们玩手机的常识,通知应该自动消失才对
//为builder设置如下属性即可达到点击后通知消失的目的
builder.setAutoCancel(true)
通知的优先级
第一行代码中优先级是通过NotificationCompat.setPriority设置的
但是由于8.0出来了,我们可以在NotificationChannel中设置,其第三个参数就是优先等级
各等级效果图
IMPORTANCE_NONE = 0:什么都没有..
-
IMPORTANCE_MIN = 1:仅通知折叠显示
-
IMPORTANCE_LOW = 2:通知栏,状态栏皆有提示,白色正方形就是通知的状态栏图标
IMPORTANCE_DEFAULT = 3:不仅通知栏状态栏有显示,而且还会有声音提示...
-
IMPORTANCE_HIGH = 4:在3的基础上增加弹窗提示