Notification的做用android
Notification是一種全局效果的通知,在系統的通知欄中顯示。既然做爲通知,其基本做用有:併發
Notification的基本操做:app
Notification的基本操做主要有建立、更新和取消三種。一個Notification的必要屬性有三項,若是不設置的話在運行時會拋出異常:ide
除了以上三項,其餘均爲可選項,不過通常而言,通知須要有交互的功能,因此通常Notification具備Action屬性,這樣就能跳轉到App的某一個Activity、啓動一個service或者發送一個Broadcast。佈局
當系統受到通知時,能夠經過震動、鈴聲、呼吸燈等多種方式進行提醒。ui
下面就從Notification的基本操做逐條介紹:this
Notification的建立過程主要涉及到Notification.Builder、Notification、NotificationManagerspa
Notification.Builder:對象
使用建造者模式構建Notification對象。因爲Notification.Builder僅支持Android4.1及以後的版本,爲了解決兼容性的問題,使用V4兼容庫中的NotifivationCompat.Builder類。blog
Notification:通知對應類,保存通知相關的數據。NotificationManager向系統發送通知時會用到。
NotificationManager:通知管理類,調用NotificationManager的notify方法能夠向系統發送通知。
獲取 NotificationManager 對象:
NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
前面講到,Notification有三個必要屬性以及一個頗有必要的屬性Action。下面咱們就建立一個簡單的Notification,主要有如下三步:
private void sendNotification(){ Intent intent = new Intent(this,SettingsActivity.class); PendingIntent mPendingIntent = PendingIntent.getActivity(this,0,intent,PendingIntent.FLAG_ONE_SHOT); NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); NotificationCompat.Builder builder = (NotificationCompat.Builder) new NotificationCompat.Builder(this) //設置小圖標 .setSmallIcon(R.mipmap.ic_launcher) //點擊後自動清除 .setAutoCancel(true) //設置通知標題 .setContentTitle("最簡單的通知") //設置通知內容 .setContentText("真的很簡單很簡單很簡單") //設置通知的動做 .setContentIntent(mPendingIntent) //設置通知時間,默認爲系統發出通知的時間 .setWhen(System.currentTimeMillis()); //第一個參數爲Notification的id notificationManager.notify(2,builder.build()); }
其中爲了實現Action屬性,咱們須要建立Intent、PendingIntent和setContentIntent()這幾步。
不難發現,其中的PendingIntent的設置纔是其中的關鍵。
PendingIntent支持三種待定的意圖:啓動Activity,啓動Service和發送Broadcast。對應於它的三個接口方法。
static PendingIntent |
getActivity(Context context,int requestCode,Intent intent,int flags) 獲取一個PendingIntent,該意圖發生時,至關於Context.startActivity(Intent) |
static PendingIntent |
getService (Context context,int requestCode,Intent intent,int flags) 獲取一個PendingIntent,該意圖發生時,至關於Context.startService (Intent) |
static PendingIntent |
getBroadcast(Context context,int requestCode,Intent intent,int flags) 獲取一個PendingIntent,該意圖發生時,至關於Context.sendBroadcast(Intent) |
其中context和intent不須要講,主要說一下requestCode和flags。其中requestCode是PendingIntent發送發的請求碼,多數狀況下設置爲0便可,requestCode會影響到flags的效果。
PendingIntent相同:Intent相同且requestCode也相同。(Intent相同須要ComponentName和intent-filter相同)
flags的常見類型有:
FLAG_ONE_SHOT:只能被使用一次,而後就會被自動cancel,若是後續還有相同的PendingIntent。那麼他們的send方法就會調用失敗。
FLAG_NO_CREATE:若是當前系統中不存在相同的PendingIntent對象,系統不會建立該PendingIntent對象,而是直接返回null。(不多使用)
FLAG_CANCEL_CURRENT:若是當前系統中已經存在一個相同的 PendingIntent 對象,那麼就將先將已有的 PendingIntent 取消,而後從新生成一個 PendingIntent 對象。
FLAG_UPDATE_CURRENT:當前描述的PendingIntent若是已經存在,那麼它們會被更新,即Intent中的Extras會被替換到最新的。
更新通知的操做很簡單,只須要再次發送一次相同ID的通知便可,若是以前的通知尚未被取消,則會直接更新該通知相關的屬性;若是以前的通知已經被取消,則會從新建立一個新的通知。
更新通知和發送通知採用一樣的方法。
取消通知的方式主要有如下5種:
若是是經過NotificationManager.notify(String tag, int id, Notification notify) 方法建立的通知,那麼只能經過 NotificationManager.cancel(String tag, int id) 或cancelAll()方法才能清除對應的通知,調用NotificationManager.cancel(int id) 無效。
前面提到了Notification的通知效果,有了通知效果更能提醒用戶去查看Notification。
Notification的通知效果有震動、呼吸燈、鈴聲三種,能夠經過builder中的setDefaults(int defaults)方法來設置,屬性有如下四種,一旦設置了默認效果,自定義效果就會失效。
//添加默認震動效果,須要申請震動權限 //<uses-permission android:name="android.permission.VIBRATE" /> Notification.DEFAULT_VIBRATE //添加系統默認聲音效果,設置此值後,調用setSound()設置自定義聲音無效 Notification.DEFAULT_SOUND //添加默認呼吸燈效果,使用時須與 Notification.FLAG_SHOW_LIGHTS 結合使用,不然無效 Notification.DEFAULT_LIGHTS //添加上述三種默認提醒效果 Notification.DEFAULT_ALL
鈴聲:
//調用系統默認響鈴,設置此屬性後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))
震動:
long[] vibrate = new long[]{0, 500, 1000, 1500}; //使用系統默認的震動參數,會與自定義的衝突 //.setDefaults(Notification.DEFAULT_VIBRATE) //自定義震動效果 .setVibrate(vibrate);
呼吸燈
//ledARGB 表示燈光顏色、 ledOnMS 亮持續時間、ledOffMS 暗的時間 .setLights(0xFF0000, 3000, 3000);
另外一種方式:
Notification notification = builder.build(); //只有在設置了標誌符Flags爲Notification.FLAG_SHOW_LIGHTS的時候,才支持呼吸燈提醒。 notify.flags = Notification.FLAG_SHOW_LIGHTS; //設置lights參數的另外一種方式 //notify.ledARGB = 0xFF0000; //notify.ledOnMS = 500; //notify.ledOffMS = 5000;
還能夠經過如下幾種Flag來設置通知效果
//提醒效果經常使用 Flag //三色燈提醒,在使用三色燈提醒時候必須加該標誌符 Notification.FLAG_SHOW_LIGHTS //發起正在運行事件(活動中) Notification.FLAG_ONGOING_EVENT //讓聲音、振動無限循環,直到用戶響應 (取消或者打開) Notification.FLAG_INSISTENT //發起Notification後,鈴聲和震動均只執行一次 Notification.FLAG_ONLY_ALERT_ONCE //用戶單擊通知後自動消失 Notification.FLAG_AUTO_CANCEL //只有調用NotificationManager.cancel()時纔會清除 Notification.FLAG_NO_CLEAR //表示正在運行的服務 Notification.FLAG_FOREGROUND_SERVICE
上面講到的Notification的佈局都是系統默認的,固然有時候處於需求,咱們可能須要自定義Notification的佈局。
那如何實現Notification的自定義佈局呢?
這裏就須要提出一個新的知識點RemoteView,望文生義,即遠程View。
RemoteView表示的是一種View結構,它能夠在其餘進程中顯示(具體來說是SystemServer進程),因爲它是在其餘進程中顯示,爲了更新它的界面,咱們不能簡單地使用普通View的那一套方法,RemoteView提供了一系列Set方法用於更新界面。
下面就是一個簡單的示例;
package com.pignet.remoteviewtest; import android.app.Notification; import android.app.NotificationManager; import android.app.PendingIntent; import android.content.Context; import android.content.Intent; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.view.View; import android.widget.Button; import android.widget.RemoteViews; public class MainActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); Button btnNotification = (Button) findViewById(R.id.btn_notification); btnNotification.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { sendNotification(); } }); } private void sendNotification(){ NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); Notification notification =new Notification(); notification.icon=R.mipmap.ic_launcher; notification.when=System.currentTimeMillis(); notification.flags=Notification.FLAG_AUTO_CANCEL; //跳轉意圖 Intent intent = new Intent(this,SettingsActivity.class); //創建一個RemoteView的佈局,並經過RemoteView加載這個佈局 RemoteViews remoteViews = new RemoteViews(getPackageName(),R.layout.layout_notification); //爲remoteView設置圖片和文本 remoteViews.setTextViewText(R.id.message,"第一條通知"); remoteViews.setImageViewResource(R.id.image,R.mipmap.ic_launcher_round); //設置PendingIntent PendingIntent pendingIntent = PendingIntent.getActivity(this,0,intent,PendingIntent.FLAG_UPDATE_CURRENT); //爲id爲openActivity的view設置單擊事件 remoteViews.setOnClickPendingIntent(R.id.openActivity,pendingIntent); //將RemoteView做爲Notification的佈局 notification.contentView =remoteViews; //將pendingIntent做爲Notification的intent,這樣當點擊其餘部分時,也能實現跳轉 notification.contentIntent=pendingIntent; notificationManager.notify(1,notification); } }
有圖: