今天,简单讲讲android里如何使Notification。

之前,我讲如何使用服务器进行版本升级时提到了Notification。这个其实我并不常用,所以当时看代码时也是查找了资料,这个很多地方还是被用到的。这里记录一下。

先看看通知栏的效果:

Notification

  Notification,俗称通知,是一种具有全局效果的通知,它展示在屏幕的顶端,首先会表现为一个图标的形式,当用户向下滑动的时候,展示出通知具体的内容。

  因为Android的快速发展,而Android的版本也快速的升级导致了一些兼容性的问题。对于Notification而言,Android3.0是一个分水岭,在其之前构建Notification推荐使用NotificationCompate.Builder,它位于android.support.v4.app.NotificationCompat.Builder,是一个Android向下版本的兼容包,而在Android3.0之后,一般推荐使用Notification.Builder构建。本博客主要介绍的是Android4.x的开发,所以在这里使用Notification.Builder进行讲解演示。

  通知一般通过NotificationManager服务发送一个Notification对象来完成通知,NotificationManager是一个重要的系统级服务,该对象位于应用程序的框架层中,应用程序可以通过它向系统发送全局的通知。使用通知的时候,需要创建一个Notification对象用来承载通知的内容,但是一般不会直接通过Notification的构造方法来得到对象,而是使用它的内部类Notification.Builder来实例化一个Builder对象,并设置通知的各项属性,最后通过Notification.Builder.builder()方法得到一个Notification对象,当获得这个Notification对象之后,就可以使用NotificationManager.notify()方法发送通知。

  NotificationManager类是一个通知管理器类,这个对象是由系统维护的服务,是以单例模式的方式获得,所以一般并不直接实例化这个对象。在Activity中,可以使用Activity.getSystemService(String)方法获取NotificationManager对象,Activity.getSystemService(String)方法可以通过Android系统级服务的句柄,返回对应的对象。在这里需要返回NotificationManager,所以直接传递Context.NOTIFICATION_SERVICE即可。

  虽然通知中提供了各种属性的设置,但是一个通知对象,有几个属性是必须要设置的,其他的属性均是可选的,必须设置的属性如下:

  • 小图标,使用setSamllIcon()方法设置。
  • 标题,使用setContentTitle()方法设置。
  • 文本内容,使用setContentText()方法设置。

更新与移除通知

  在使用NotificationManager.notify()发送通知的时候,需要传递一个标识符,用于唯一标识这个通知。对于有些场景,并不是无限的添加新的通知,有时候需要更新原有通知的信息,这个时候可以重写构建Notification,而使用与之前通知相同标识符来发送通知,这个时候旧的通知就被被新的通知所取代,起到更新通知的效果。

  对于一个通知,当展示在状态栏之后,但是使用过后,如何取消呢?Android为我们提供两种方式移除通知,一种是Notification自己维护,使用setAutoCancel()方法设置是否维护,传递一个boolean类型的数据。另外一种方式使用NotificationManager通知管理器对象来维护,它通过notify()发送通知的时候,指定的通知标识Id来操作通知,可以使用cancel(int)来移除一个指定的通知,也可以使用cancelAll()移除所有的通知。

  使用NotificationManager移除指定通知示例:

   NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);mNotificationManager.cancel(0);

PendingIntent

  对于一个通知而言,它显示的消息是有限的,一般仅用于提示一些概要信息。但是一般简短的消息,并不能表达需要告诉用户的全部内容,所以需要绑定一个意图,当用户点击通知的时候,调用一个意图展示出一个Activity用来显示详细的内容。而Notification中,并不使用常规的Intent去传递一个意图,而是使用PendingIntent。

  先来说说Intent和PendingIntent的区别,PendingIntent可以看做是对Intent的包装,通过名称可以看出PendingIntent用于处理即将发生的意图,而Intent用来用来处理马上发生的意图。而对于通知来说,它是一系统级的全局通知,并不确定这个意图被执行的时间。当在应用外部执行PendingIntent时,因为它保存了触发应用的Context,使得外部应用可以如在当前应用中一样,执行PendingIntent里的Intent,就算执行的时候响应通知的应用已经被销毁了,也可以通过存在PendingIntent里的Context照常执行它,并且还可以处理Intent说带来的额外信息。

  PendingIntent提供了多个静态的getXxx()方法,用于获得适用于不同场景的PendingIntent对象。一般需要传递的几个参数都很常规,只介绍一个flag参数,用于标识PendingIntent的构造选择:

  • FLAG_CANCEL_CURRENT:如果构建的PendingIntent已经存在,则取消前一个,重新构建一个。
  • FLAG_NO_CREATE:如果前一个PendingIntent已经不存在了,将不再构建它。
  • FLAG_ONE_SHOT:表明这里构建的PendingIntent只能使用一次。
  • FLAG_UPDATE_CURRENT:如果构建的PendingIntent已经存在,则替换它,常用。

Notification视觉风格

  Notification有两种视觉风格,一种是标准视图(Normal view)、一种是大视图(Big view)。标准视图在Android中各版本是通用的,但是对于大视图而言,仅支持Android4.1+的版本。

  从官方文档了解到,一个标准视图显示的大小要保持在64dp高,宽度为屏幕标准。标准视图的通知主体内容有一下几个:

  1. 通知标题。
  2. 大图标。
  3. 通知内容。
  4. 通知消息。
  5. 小图标。
  6. 通知的时间,一般为系统时间,也可以使用setWhen()设置。
  1.   下面通过一个示例,模仿上面效果的通知。

1.通知标题。
2.大图标。
3.通知内容。
4.通知消息。
5.小图标。
6.通知的时间,一般为系统时间,也可以使用setWhen()设置。

  下面通过一个示例,模仿上面效果的通知。

btnNotification.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {Bitmap btm = BitmapFactory.decodeResource(getResources(),R.drawable.msg);NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(MainActivity.this).setSmallIcon(R.drawable.msg).setContentTitle("5 new message").setContentText("twain@android.com");mBuilder.setTicker("New message");//第一次提示消息的时候显示在通知栏上mBuilder.setNumber(12);mBuilder.setLargeIcon(btm);mBuilder.setAutoCancel(true);//自己维护通知的消失//构建一个IntentIntent resultIntent = new Intent(MainActivity.this,ResultActivity.class);//封装一个IntentPendingIntent resultPendingIntent = PendingIntent.getActivity(MainActivity.this, 0, resultIntent,PendingIntent.FLAG_UPDATE_CURRENT);// 设置通知主题的意图mBuilder.setContentIntent(resultPendingIntent);//获取通知管理器对象NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);mNotificationManager.notify(0, mBuilder.build());}});

显示效果:

进度条样式的通知

  对于一个标准通知,有时候显示的消息并不一定是静态的,还可以设定一个进度条用于显示事务完成的进度。

  Notification.Builder类中提供一个setProgress(int max,int progress,boolean indeterminate)方法用于设置进度条,max用于设定进度的最大数,progress用于设定当前的进度,indeterminate用于设定是否是一个确定进度的进度条。通过indeterminate的设置,可以实现两种不同样式的进度条,一种是有进度刻度的(true),一种是循环流动的(false)。下面分别用两个示例演示:

  有进度的进度条,实现代码:

btnProgreNotification.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {manager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);builder = new NotificationCompat.Builder(MainActivity.this).setSmallIcon(R.drawable.ic_launcher).setContentTitle("Picture Download").setContentText("Download in progress");builder.setAutoCancel(true);//通过一个子线程,动态增加进度条刻度new Thread(new Runnable() {@Overridepublic void run() {int incr;for (incr = 0; incr <= 100; incr += 5) {builder.setProgress(100, incr, false);manager.notify(0, builder.build());try {Thread.sleep(300);} catch (InterruptedException e) {Log.i(TAG, "sleep failure");}}builder.setContentText("Download complete").setProgress(0, 0, false);manager.notify(0, builder.build());}}).start();}});

 显示效果:

对于循环流动的进度条,下面是实现代码:

btnProNotification.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {manager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);builder = new NotificationCompat.Builder(MainActivity.this).setSmallIcon(R.drawable.ic_launcher).setContentTitle("Picture Download").setContentText("Download in progress");builder.setProgress(0, 0, true);//设置为true,表示流动manager.notify(0, builder.build());//5秒之后还停止流动new Thread(new Runnable() {@Overridepublic void run() {try {Thread.sleep(5000);} catch (InterruptedException e) {e.printStackTrace();}builder.setProgress(100, 100, false);//设置为true,表示刻度manager.notify(0, builder.build());}}).start();}});

自定义通知

  和Toast一样,通知也可以使用自定义的XML来自定义样式,但是对于通知而言,因为它的全局性,并不能简单的通过inflate膨胀出一个View,因为可能触发通知的时候,响应的App已经关闭,无法获取当指定的XML布局文件。所以需要使用单独的一个RemoteViews类来操作。

  RemoteViews,描述了一个视图层次的结构,可以显示在另一个进程。层次结构也是从布局文件中“膨胀”出一个视图,这个类,提供了一些基本的操作求改其膨胀的内容。

  RemoteViews提供了多个构造函数,一般使用RemoteViews(String packageName,int layoutId)。第一个参数为包的名称,第二个为layout资源的Id。当获取到RemoteViews对象之后,可以使用它的一系列setXxx()方法通过控件的Id设置控件的属性。最后使用NotificationCompat.Builder.setContent(RemoteViews)方法设置它到一个Notification中。

  下面通过一个示例展示它:

  自定义的布局XML代码:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="match_parent"android:padding="10dp" ><ImageViewandroid:id="@+id/imageNo"android:layout_width="wrap_content"android:layout_height="match_parent"android:layout_alignParentLeft="true"android:layout_marginRight="10dp" /><TextViewandroid:id="@+id/titleNo"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_toRightOf="@id/imageNo" /><TextViewandroid:id="@+id/textNo"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_below="@id/titleNo"android:layout_toRightOf="@id/imageNo" /></RelativeLayout>

实现代码:

btnCustomNotification.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {RemoteViews contentViews = new RemoteViews(getPackageName(),R.layout.custom_notification);//通过控件的Id设置属性contentViews.setImageViewResource(R.id.imageNo, R.drawable.btm1);contentViews.setTextViewText(R.id.titleNo, "自定义通知标题");contentViews.setTextViewText(R.id.textNo, "自定义通知内容");Intent intent = new Intent(MainActivity.this,ResultActivity.class);PendingIntent pendingIntent = PendingIntent.getActivity(MainActivity.this, 0, intent,PendingIntent.FLAG_CANCEL_CURRENT);NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(MainActivity.this).setSmallIcon(R.drawable.ic_launcher).setContentTitle("My notification").setTicker("new message");mBuilder.setAutoCancel(true);mBuilder.setContentIntent(pendingIntent);mBuilder.setContent(contentViews);mBuilder.setAutoCancel(true);NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);mNotificationManager.notify(10, mBuilder.build());}});

效果展示:

设定提示响应

  对于有些通知,需要调用一些设备的资源,使用户能更快的发现有新通知,一般可设定的响应有:铃声、闪光灯、震动。对于这三个属性,NotificationCompat.Builder提供了三个方法设定:

  • setSound(Uri sound):设定一个铃声,用于在通知的时候响应。传递一个Uri的参数,格式为“file:///mnt/sdcard/Xxx.mp3”。
  • setLights(int argb, int onMs, int offMs):设定前置LED灯的闪烁速率,持续毫秒数,停顿毫秒数。
  • setVibrate(long[] pattern):设定震动的模式,以一个long数组保存毫秒级间隔的震动。

  大多数时候,我们并不需要设定一个特定的响应效果,只需要遵照用户设备上系统通知的效果即可,那么可以使用setDefaults(int)方法设定默认响应参数,在Notification中,对它的参数使用常量定义了,我们只需使用即可:

  • DEFAULT_ALL:铃声、闪光、震动均系统默认。
  • DEFAULT_SOUND:系统默认铃声。
  • DEFAULT_VIBRATE:系统默认震动。
  • DEFAULT_LIGHTS:系统默认闪光。

  而在Android中,如果需要访问硬件设备的话,是需要对其进行授权的,所以需要在清单文件AndroidManifest.xml中增加两个授权,分别授予访问振动器与闪光灯的权限:

     <!-- 闪光灯权限 --><uses-permission android:name="android.permission.FLASHLIGHT"/><!-- 振动器权限 --><uses-permission android:name="android.permission.VIBRATE"/>

这里简单举一个调用特定的响应效果的例子:

/**
* 最普通的通知效果
*/
private void showNotifyOnlyText() {NotificationCompat.Builder builder = new NotificationCompat.Builder(this).setSmallIcon(R.mipmap.ic_launcher).setLargeIcon(mLargeIcon).setContentTitle("我是只有文字效果的通知").setContentText("我没有铃声、震动、呼吸灯,但我就是一个通知");mManager.notify(1, builder.build());
}/**
* 展示有自定义铃声效果的通知
* 补充:使用系统自带的铃声效果:Uri.withAppendedPath(Audio.Media.INTERNAL_CONTENT_URI, "6");
*/
private void showNotifyWithRing() {NotificationCompat.Builder builder = new NotificationCompat.Builder(this).setSmallIcon(R.mipmap.ic_launcher).setContentTitle("我是伴有铃声效果的通知").setContentText("美妙么?安静听~")//调用系统默认响铃,设置此属性后setSound()会无效//.setDefaults(Notification.DEFAULT_SOUND)//调用系统多媒体裤内的铃声//.setSound(Uri.withAppendedPath(MediaStore.Audio.Media.INTERNAL_CONTENT_URI,"2"));//调用自己提供的铃声,位于 /res/values/raw 目录下.setSound(Uri.parse("android.resource://com.littlejie.notification/" + R.raw.sound));//另一种设置铃声的方法//Notification notify = builder.build();//调用系统默认铃声//notify.defaults = Notification.DEFAULT_SOUND;//调用自己提供的铃声//notify.sound = Uri.parse("android.resource://com.littlejie.notification/"+R.raw.sound);//调用系统自带的铃声//notify.sound = Uri.withAppendedPath(MediaStore.Audio.Media.INTERNAL_CONTENT_URI,"2");//mManager.notify(2,notify);mManager.notify(2, builder.build());
}/**
* 展示有震动效果的通知,需要在AndroidManifest.xml中申请震动权限
* <uses-permission android:name="android.permission.VIBRATE" />
* 补充:测试震动的时候,手机的模式一定要调成铃声+震动模式,否则你是感受不到震动的
*/
private void showNotifyWithVibrate() {//震动也有两种设置方法,与设置铃声一样,在此不再赘述long[] vibrate = new long[]{0, 500, 1000, 1500};NotificationCompat.Builder builder = new NotificationCompat.Builder(this).setSmallIcon(R.mipmap.ic_launcher).setContentTitle("我是伴有震动效果的通知").setContentText("颤抖吧,凡人~")//使用系统默认的震动参数,会与自定义的冲突//.setDefaults(Notification.DEFAULT_VIBRATE)//自定义震动效果.setVibrate(vibrate);//另一种设置震动的方法//Notification notify = builder.build();//调用系统默认震动//notify.defaults = Notification.DEFAULT_VIBRATE;//调用自己设置的震动//notify.vibrate = vibrate;//mManager.notify(3,notify);mManager.notify(3, builder.build());
}/**
* 显示带有呼吸灯效果的通知,但是不知道为什么,自己这里测试没成功
*/
private void showNotifyWithLights() {final NotificationCompat.Builder builder = new NotificationCompat.Builder(this).setSmallIcon(R.mipmap.ic_launcher).setContentTitle("我是带有呼吸灯效果的通知").setContentText("一闪一闪亮晶晶~")//ledARGB 表示灯光颜色、 ledOnMS 亮持续时间、ledOffMS 暗的时间.setLights(0xFF0000, 3000, 3000);Notification notify = builder.build();//只有在设置了标志符Flags为Notification.FLAG_SHOW_LIGHTS的时候,才支持呼吸灯提醒。notify.flags = Notification.FLAG_SHOW_LIGHTS;//设置lights参数的另一种方式//notify.ledARGB = 0xFF0000;//notify.ledOnMS = 500;//notify.ledOffMS = 5000;//使用handler延迟发送通知,因为连接usb时,呼吸灯一直会亮着Handler handler = new Handler();handler.postDelayed(new Runnable() {@Overridepublic void run() {mManager.notify(4, builder.build());}}, 10000);
}/**
* 显示带有默认铃声、震动、呼吸灯效果的通知
* 如需实现自定义效果,请参考前面三个例子
*/
private void showNotifyWithMixed() {NotificationCompat.Builder builder = new NotificationCompat.Builder(this).setSmallIcon(R.mipmap.ic_launcher).setContentTitle("我是有铃声+震动+呼吸灯效果的通知").setContentText("我是最棒的~")//等价于setDefaults(Notification.DEFAULT_SOUND | Notification.DEFAULT_LIGHTS | Notification.DEFAULT_VIBRATE);.setDefaults(Notification.DEFAULT_ALL);mManager.notify(5, builder.build());
}/**
* 通知无限循环,直到用户取消或者打开通知栏(其实触摸就可以了),效果与FLAG_ONLY_ALERT_ONCE相反
* 注:这里没有给Notification设置PendingIntent,也就是说该通知无法响应,所以只能手动取消
*/
private void showInsistentNotify() {NotificationCompat.Builder builder = new NotificationCompat.Builder(this).setSmallIcon(R.mipmap.ic_launcher).setContentTitle("我是一个死循环,除非你取消或者响应").setContentText("啦啦啦~").setDefaults(Notification.DEFAULT_ALL);Notification notify = builder.build();notify.flags |= Notification.FLAG_INSISTENT;mManager.notify(6, notify);
}/**
* 通知只执行一次,与默认的效果一样
*/
private void showAlertOnceNotify() {NotificationCompat.Builder builder = new NotificationCompat.Builder(this).setSmallIcon(R.mipmap.ic_launcher).setContentTitle("仔细看,我就执行一遍").setContentText("好了,已经一遍了~").setDefaults(Notification.DEFAULT_ALL);Notification notify = builder.build();notify.flags |= Notification.FLAG_ONLY_ALERT_ONCE;mManager.notify(7, notify);
}/**
* 清除所有通知
*/
private void clearNotify() {mManager.cancelAll();
}

简单讲讲,其实Notification我也不熟,这里的内容大部分是网上那些博客专家那里拷贝过来的。首先,在Android3.0之前使用nCompate.Builder创建Notification,Android3.0之后,使用Notification.Builder构建Notification。然后使用setSamllIcon(),setContentTitle(),setContentTitle()等函数设置Notification的属性,具体的代码里写的很详细。还可以使用mBuilder.setContentIntent(resultPendingIntent)设置通知主题的意图,即点击后如何跳转。最后使用getSystemService(Context.NOTIFICATION_SERVICE);获取NotificationManager ,使用NotificationManager.notify()方法发送通知。

android Notification的使用就讲完了。

就这么简单。

android Notification的使用相关推荐

  1. Android Notification实现推送消息过程中接受到消息端有声音及震动及亮屏提示

    在Android Notification状态栏通知一文中,简单实现了消息的推送效果,这里就接着上文说一下,当用户接受到消息时的提示效果 // 5-加入震动及声音及亮屏 notification.de ...

  2. Android Notification状态栏通知

    没有增加额外的震动及声音效果,这里直接实现了通知的功能,看效果吧: MainActivity.java package com.example.notification;import android. ...

  3. Android Notification总结

    Android Notification总结 目录[-] 一.通知的主要功能 二.通知简介 三.通知的使用流程 四.使用NotificationCompat.Builder设置通知的属性: 五.管 ...

  4. Android Notification通知详解

    Android Notification通知详解 Notification: (一).简介: 显示在手机状态栏的通知.Notification所代表的是一种具有全局效果的通知,程序一般通过Notifi ...

  5. android notification应用之自定义来电通知

    android notification应用之自定义来电通知 1.为了实现老板的各种要求 本人矜矜业业完成任务 随着这个软电话软件的日益完善 本来来电的时候是创建一条通知点亮屏幕 用户可以解锁屏幕后接 ...

  6. Android Notification 详解——基本操作

    Android Notification 详解 版权声明:本文为博主原创文章,未经博主允许不得转载. 前几天项目中有用到 Android 通知相关的内容,索性把 Android Notificatio ...

  7. Android Notification通知详细解释

    Android Notification通知具体解释 Notification: (一).简单介绍: 显示在手机状态栏的通知. Notification所代表的是一种具有全局效果的通知,程序一般通过N ...

  8. android系统通知栏的弹框流程,Android Notification 手机系统横幅弹出提示框调用

    类似于仿微信信息提示提出框. 在项目当中集成了推送功能,当手机接收到消息后只是在手机通知栏有提示信息.所以需要展示像微信信息弹出框一样的效果,开始自己还以为微信信息弹出框是自定义Dialog之类的自定 ...

  9. Android Notification 详解

    下图是我对 Notification 做的思维导图,也是本文的主要逻辑.  本文主要讲述 Notification 的基本操作部分,进阶部分的内容还在学习ing~ Notification 概述 N ...

最新文章

  1. iOS socket
  2. sugar linux桌面,Sugar一个Linux的Distro和学习平台为孩子们 | MOS86
  3. GDCM:gdcm::SOPClassUIDToIOD的测试程序
  4. iqn怎么查 linux_程序员必备:46个Linux面试常见问题!收藏!
  5. 向算法传递函数:谓词
  6. [深度学习] 自然语言处理---Transformer 位置编码介绍
  7. Oracle技术之ASM上恢复STANDBY数据库出现ORA-15173错误
  8. cxVerticalGrid赋值是实时更新
  9. ADMM算法理论与应用
  10. SteamVR简介(Yanlz+Steam+VR+Unity+AR+MR+XR+=)
  11. linux误删除文件恢复
  12. android+微博点赞动画,模仿微博点赞动画
  13. 微信营销与微博营销的区别
  14. 【短信】谷歌4.4短信代码学习
  15. debian系linux,更换apt-get官方源为国内源
  16. AtCoder Beginner Contest 153 题解
  17. 机器学习分类器模型评价指标
  18. CAP与ACID原则
  19. HTTP协议之vary
  20. 300个韩国网站欣赏

热门文章

  1. 第二次冲刺阶段(第七天)
  2. modelform save
  3. MySQL及其分支或衍生版
  4. UVA 321 The New Villa
  5. 仙剑4按键取钱的东东。
  6. android java json与实体互相转换工具
  7. 创建 linuxrc 文件
  8. set hive.map.aggr=true 时统计PV数据错误
  9. 批量解锁源代码管理器的文件命
  10. [Objective-c 基础 - 2.1] 封装