通知是系统内部的一项通知服务,管理屏幕上方的通知栏或状态栏
具有以下特点:
不干扰用户,可让用户专注操作.
只要用户不清空一直保留在状态栏上.
具有全局效果.
原理可分为:
服务端:通知管理器 NotificationManager对象
客户端:Notification对象 (封装通知内容,图标,挂起的intent)
使用了PendingIntent对象
挂起intent,将intent存储到PendingIntent对象里面,以后从这里拿出来使用
即使调用它的进程结束该PendingIntent还可以启动目标组件.
PendingIntent由系统内部维护,与创建它的进程无关.
状态栏下滑PendingIntent可调用活动,服务,接收器
getActivity(Context, int, Intent, int)
getBroadcast(Context, int, Intent, int)
getService(Context, int, Intent, int)
为了便于测试,PendingIntent绑定的是一个活动,都是用通知去启动同一个活动。
1.老API版本方法
通知的写法大致可以分成四个步骤,如下:
// 1.获得通知管理器(服务端)
NotificationManager manager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
// 2.创建通知对象(客户端)
int icon = R.drawable.ic_launcher;// 图标
CharSequence tickerText = "通知提示";
long when = System.currentTimeMillis();// 立即发送不延时
Notification notification = new Notification(icon, tickerText, when);
// 3.定义 PendingIntent(挂起的Intent,Intent的包装类,在没有处理之前不会随着任何事情的改变而消失)
Context context = getApplicationContext();
CharSequence contentTitle = "My notification title";// 通知的标题
CharSequence contentText = "Hello World!";// 通知的摘要
Intent notifycationIntent = new Intent(this, MyActivity.class);// 通知的处理-->>启动一个活动
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, notifycationIntent, 0);
// 将挂起的PendingIntent绑定给通知对象
notification.setLatestEventInfo(context, contentTitle, contentText, contentIntent);
// 4.发送通知
manager.notify(NOTIFY_ID1, notification);//NOTIFY_ID1通知的身份标签id,用于识别身份(数值常量)
2.新API版本方法
此方法区别是在第三步将通知对象用Builder进行打包处理,需要api 11及更高版本的支持。
//1.获得通知管理器(服务端)
NotificationManager manager=(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
//2.定义 PendingIntent,可以是活动,广播或服务
Intent notificationIntent = new Intent(this, MyActivity.class);
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, notificationIntent, 0);
//3.创建通知对象(客户端)
Notification.Builder builder = new Notification.Builder(this);
builder.setContentTitle("通知标题");
builder.setContentText("通知摘要");
builder.setTicker("通知提示");
builder.setSmallIcon(R.drawable.ic_launcher);//小图标
builder.setLargeIcon(BitmapFactory.decodeResource(getResources(), R.drawable.ic_launcher));//大图标
builder.setAutoCancel(true);//自动取消
builder.setContentInfo("contentinfo");
builder.setDefaults(Notification.DEFAULT_ALL);//默认提示效果,是否有声音,震动,闪光等等
builder.setContentIntent(contentIntent);//绑定PendingIntent
long when = System.currentTimeMillis();//立即发送不延时
builder.setWhen(when);//发送延时
Notification notification = builder.getNotification();//得到通知
//4.发送通知
manager.notify(NOTIFY_ID2, notification);//NOTIFY_ID2身份id
3.兼容版本方法
和新版本方法一致,只是Builder类使用了兼容包中NotificationCompat的Builder,其他步骤一样。
//1.获得通知管理器(服务端)
NotificationManager manager=(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
//2.定义 PendingIntent
Intent notificationIntent = new Intent(this, MyActivity.class);
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, notificationIntent, 0);
//3.创建通知对象(客户端)
NotificationCompat.Builder builder = new NotificationCompat.Builder(this);//使用兼容包的NotificationCompat.Builder
builder.setContentTitle("通知标题");
builder.setContentText("通知摘要");
builder.setTicker("通知提示");
builder.setSmallIcon(R.drawable.ic_launcher);//小图标
builder.setLargeIcon(BitmapFactory.decodeResource(getResources(), R.drawable.ic_launcher));//大图标
builder.setAutoCancel(true);//自动取消
builder.setContentInfo("contentinfo");
builder.setDefaults(Notification.DEFAULT_ALL);//默认提示效果,是否有声音,震动,闪光等等
builder.setContentIntent(contentIntent);//绑定PendingIntent
long when = System.currentTimeMillis();//立即发送不延时
builder.setWhen(when);//发送延时
Notification notification = builder.build();//得到通知
// Notification notification = builder.getNotification();//过时的方法
// notification.flags=Notification.FLAG_AUTO_CANCEL; //设置自动取消
// notification.flags=Notification.FLAG_NO_CLEAR; //不可取消(只能通过id进行取消)
notification.flags=notification.FLAG_ONGOING_EVENT;//通知放置在正在运行
//4.发送通知
manager.notify(NOTIFY_ID3, notification);
4.自定义通知视图
前面的方法都是使用的系统的通知样式,这里我们自己定义自己的通知视图,从而可以得到我们想要的不一样的视图布局。
为了便于测试,我们自定义一个简单的布局文件,文件名为notify.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/RelativeLayout1"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<ImageView
android:id="@+id/icon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true"
android:layout_marginLeft="15dp"
android:layout_marginTop="15dp"
android:src="@drawable/psb" />
<TextView
android:id="@+id/txt_Title"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignTop="@+id/icon"
android:layout_marginLeft="22dp"
android:layout_toRightOf="@+id/icon"
android:text="TextView" />
<TextView
android:id="@+id/txt_info"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignLeft="@+id/txt_Title"
android:layout_below="@+id/txt_Title"
android:text="TextView" />
</RelativeLayout>
通知栏的布局是用RemoteViews(也称远程视图)的视图来完成的,不过,RemoteViews在使用上会有一些限制。
java代码部分也可以大致分为五个步骤,如下:
//1.获得通知管理器(服务端)
NotificationManager manager=(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
//2 创建和设置远程视图
RemoteViews contentView = new RemoteViews(getPackageName(), R.layout.notify);
//设置远程视图中的控件内容
contentView.setImageViewResource(R.id.icon, R.drawable.psb);
contentView.setTextViewText(R.id.txt_Title, "我的通知标题");
contentView.setTextViewText(R.id.txt_info, "我的通知信息");
//3 创建通知对象
Notification notification = new Notification(R.drawable.ic_launcher, "我的提示", System.currentTimeMillis());//使用带参数的构造方法,要不无法显示出通知
//绑定远程视图
notification.contentView = contentView;
//4.定义 PendingIntent并绑定
Intent notificationIntent = new Intent(this, MyActivity.class);
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, notificationIntent, 0);
notification.contentIntent = contentIntent;//绑定 PendingIntent
notification.flags=Notification.FLAG_AUTO_CANCEL;//设置自动取消
//5 发通知
manager.notify(CUSTOM_VIEW_NOTIFYY_ID, notification);
因为通知栏通知一般是一长条的横向视图,所以布局尽量设计成合适的横向布局。
前面我们通知在发出的同时都带有一个id号,它是通知的身份标签,如果没有设置自动取消通知,通知则会一直存在,或者设置了通知的不可取消属性,如果需要取消通知,可以用id号进行取消对应的通知(或者使用id进行一些别的操作),如下:
//获取通知管理器对象
NotificationManager manager=(NotificationManager)getSystemService(Context.NOTIFICATION_SERVICE);
manager.cancel(NOTIFY_ID1);//取消对应id的通知