Android版本迭代速度很快,API也是改的很迅速,特別是Notification,很多API版本提供的方法樣式都不一樣,但是好在Android在appcompat-v7庫裏面提供了一個NofificationCompat類來處理兼容。在平時開發通知用的比較少,也沒有去總結他們,但是現在看到很多app的通知都比較炫酷,自己不熟悉心裏有個疙瘩。我們總結一些通知的類型以及使用。
通知分類
我們把通知分爲如下這四類:
- 正常視圖,經常在狀態欄看到的高度爲64dp的通知視圖;
- 在API16中引入的以Style方式展示的MediaStyle,InboxStyle,BigTexStyle,BigPictureStyle四種風格樣式
- 自定義通知通知佈局
- 在API21中加入的headsUpContentView
由於國產手機的定製我在自己的小米5Android 7.0系統上面顯示通知有一些問題,所以我們下面的分類圖以及代碼是根據Galaxy_Nexus_API_25的Android模擬器來做的。
普通通知
效果圖:
實現代碼:
NotificationManager manager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
NotificationCompat.Builder builder = new NotificationCompat.Builder(getApplicationContext());
Notification notification = builder
.setContentTitle("這是普通通知標題")
.setContentText("這是普通通知內容")
.setWhen(System.currentTimeMillis())
.setSmallIcon(R.mipmap.ic_launcher2)
.setLargeIcon(BitmapFactory.decodeResource(
getResources(), R.mipmap.ic_launcher2))
.build();
manager.notify(1, notification);
這類通知是我們平時看到App的最多的通知類型,實現代碼頁挺簡單。
API16以上的四種Style類型通知
在普通通知的基礎上面,可以增添這四種Style的類型
MediaStyle
我們通常看到音樂播放器之類的App會顯示這個通知類型。
效果圖:
注意這個可以收縮的看我們從普通的通知模式到擴展Style的顯示樣式。
實現代碼:
private void typeMedia() {
NotificationManager manager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
NotificationCompat.Builder builder = new NotificationCompat.Builder(this);
builder.setContentTitle("MediaStyle");
builder.setContentText("Song Title");
builder.setSmallIcon(R.mipmap.ic_launcher2);
builder.setLargeIcon(BitmapFactory.decodeResource(getResources(), R.mipmap.ic_launcher2));
builder.setDefaults(NotificationCompat.DEFAULT_ALL);
Intent intent = new Intent(this, ImageActivity.class);
PendingIntent pIntent = PendingIntent.getActivity(this, 1, intent, 0);
builder.setContentIntent(pIntent);
//第一個參數是圖標資源id 第二個是圖標顯示的名稱,第三個圖標點擊要啓動的PendingIntent
builder.addAction(R.drawable.ic_skip_previous_white_24dp, "", null);
builder.addAction(R.drawable.ic_stop_white_24dp, "", null);
builder.addAction(R.drawable.ic_play_arrow_white_24dp, "", pIntent);
builder.addAction(R.drawable.ic_skip_next_white_24dp, "", null);
NotificationCompat.MediaStyle style = new NotificationCompat.MediaStyle();
style.setMediaSession(new MediaSessionCompat(this, "MediaSession",
new ComponentName(MainActivity.this, Intent.ACTION_MEDIA_BUTTON), null).getSessionToken());
//CancelButton在5.0以下的機器有效
style.setCancelButtonIntent(pIntent);
style.setShowCancelButton(true);
//設置要現實在通知右方的圖標 最多三個
style.setShowActionsInCompactView(2, 3);
builder.setStyle(style);
builder.setShowWhen(false);
Notification notification = builder.build();
manager.notify(TYPE_MEDIA, notification);
}
InboxStyle
收件箱樣式,支持展示具有一串消息內容的樣式,按行顯示,適用於短信,郵件,IM等。
private void typeInboxStyle() {
NotificationCompat.InboxStyle style = new android.support.v4.app.NotificationCompat.InboxStyle();
style.setBigContentTitle("這是InboxStyle的標題");
for (int i = 0; i < 5; i++) {
style.addLine("行" + i);
}
Notification notification = builder
.setSmallIcon(R.mipmap.ic_launcher)
.setLargeIcon(BitmapFactory.decodeResource(
getResources(), R.mipmap.ic_launcher))
.setStyle(style)
.build();
manager.notify(TYPE_INBOX, notification);
}
BigTextStyle
可以顯示大段文字內容。
private void typeBigText() {
NotificationCompat.BigTextStyle style = new android.support.v4.app.NotificationCompat.BigTextStyle();
style.bigText("很長的文本很長的文本很長的文本很長的文本" +
"很長的文本很長的文本很長的文本很長的文本" +
"很長的文本很長的文本很長的文本很長的文本");
style.setBigContentTitle("這是很長的標題");
style.setSummaryText("這是很長的末尾");
Notification notification = builder
.setContentTitle("這是通知標題")
.setContentText("這是通知內容")
.setSmallIcon(R.mipmap.ic_launcher)
.setLargeIcon(BitmapFactory.decodeResource(
getResources(), R.mipmap.ic_launcher))
.setStyle(style)
.build();
manager.notify(TYPE_BIG_TEXT, notification);
}
BigPictureStyle
大圖樣式,除了在通知欄顯示標題和內容外,還可以顯示一張大圖片,最大高度爲256dp。
public void bigPictureStyle(){
NotificationCompat.Builder builder = new NotificationCompat.Builder(this);
builder.setSmallIcon(R.mipmap.ic_launcher);
builder.setDefaults(NotificationCompat.DEFAULT_ALL);
builder.setLargeIcon(BitmapFactory.decodeResource(getResources(),R.mipmap.ic_launcher));
android.support.v4.app.NotificationCompat.BigPictureStyle style = new android.support.v4.app.NotificationCompat.BigPictureStyle();
style.setBigContentTitle("BigPictureTitle");
style.setSummaryText("SummaryText");
style.bigPicture(BitmapFactory.decodeResource(getResources(),R.drawable.big_picture));
builder.setStyle(style);
builder.setAutoCancel(true);
Intent intent = new Intent(this,ImageActivity.class);
PendingIntent pIntent = PendingIntent.getActivity(this,1,intent,0);
//設置點擊大圖後跳轉
builder.setContentIntent(pIntent);
Notification notification = builder.build();
manager.notify(TYPE_BIG_PICTURE,notification);
}
自定義通知佈局
當以上的通知都無法滿足我們的需求的時候我們可以選擇RemoteViews來進行自定義通知的佈局文件。
private void typeCustom(){
builder.setSmallIcon(R.mipmap.ic_launcher);
builder.setDefaults(NotificationCompat.DEFAULT_ALL);
builder.setLargeIcon(BitmapFactory.decodeResource(getResources(),R.mipmap.ic_launcher));
RemoteViews remoteViews = new RemoteViews(getPackageName(),R.layout.statu_view);
builder.setContent(remoteViews);
Intent intent = new Intent(this,ImageActivity.class);
PendingIntent pendingIntent = PendingIntent.getActivity(this,1,intent,0);
remoteViews.setOnClickPendingIntent(R.id.reply,pendingIntent);
remoteViews.setTextViewText(R.id.title,"我是自定義標題");
remoteViews.setTextViewText(R.id.content,"我是自定義內容");
Notification notification = builder.build();
manager.notify(TYPE_CUSTOM,notification);
}
上述的設置的View我們發現是一個固定的64dp的高度。如果我們想要一個比這個高的咋辦呢,在API16引入了bigContentView它最大支持256dp。
佈局文件高度更改,代碼稍微改動一下
private void typeCustom(){
builder.setSmallIcon(R.mipmap.ic_launcher);
builder.setDefaults(NotificationCompat.DEFAULT_ALL);
builder.setLargeIcon(BitmapFactory.decodeResource(getResources(),R.mipmap.ic_launcher));
RemoteViews remoteViews = new RemoteViews(getPackageName(),R.layout.statu_view);
Notification notification = builder.build();
if(android.os.Build.VERSION.SDK_INT >= 16) {
notification = builder.build();
notification.bigContentView = remoteViews;
}
builder.setContent(remoteViews);
Intent intent = new Intent(this,ImageActivity.class);
PendingIntent pendingIntent = PendingIntent.getActivity(this,1,intent,0);
remoteViews.setOnClickPendingIntent(R.id.reply,pendingIntent);
remoteViews.setTextViewText(R.id.title,"我是自定義標題");
remoteViews.setTextViewText(R.id.content,"我是自定義內容");
manager.notify(TYPE_CUSTOM,notification);
}
關於通知佈局適配手機通知的背景顏色可以參考這篇文章:查看。其實就是通過獲取手機的通知欄顯示的顏色來決定我們的佈局顏色。
headsUpContentView
這個通知不顯示在通知欄而是以橫幅的方式顯示在應用上方。這個效果在API21上纔有效。
private void typeHeadsUpContentView(){
builder.setContentTitle("橫幅通知標題");
builder.setContentText("橫幅通知內容");
builder.setDefaults(NotificationCompat.DEFAULT_ALL);
builder.setSmallIcon(R.mipmap.ic_launcher);
builder.setLargeIcon(BitmapFactory.decodeResource(getResources(),R.mipmap.ic_launcher));
Intent intent = new Intent(this,ImageActivity.class);
PendingIntent pIntent = PendingIntent.getActivity(this,1,intent,0);
builder.setContentIntent(pIntent);
//這句是重點
builder.setFullScreenIntent(pIntent,true);
builder.setAutoCancel(true);
Notification notification = builder.build();
manager.notify(TYPE_HEAD_UP,notification);
}
開發中使用過的通知
下載通知進度
- 使用NotificationCompat.Builder.setProgress來實現
private void typeProgress() {
builder.setSmallIcon(R.mipmap.ic_launcher);
builder.setContentTitle("下載");
builder.setContentText("正在下載");
manager.notify(TYPE_PROGRESS, builder.build());
builder.setProgress(100, 0, false);
//下載以及安裝線程模擬
new Thread(new Runnable() {
@Override
public void run() {
float preProgress = 0;
//模擬下載文件的小數點的progress避免1.01,1.02都更新倒置卡死應用。
for (float progress = 0; progress < 100; progress++) {
int currProgress = (int) progress;
if (preProgress < currProgress) {
builder.setContentText(progress + "%");
builder.setProgress(100, (int) progress, false);
//下載進度提示
builder.setContentText("下載" + currProgress + "%");
manager.notify(TYPE_PROGRESS, builder.build());
}
preProgress = progress;
try {
Thread.sleep(50);//演示休眠50毫秒
} catch (InterruptedException e) {
e.printStackTrace();
}
}
//下載完成後更改標題以及提示信息
builder.setContentTitle("開始安裝");
builder.setContentText("安裝中...");
//設置進度爲不確定,用於模擬安裝
builder.setProgress(0, 0, true);
manager.notify(TYPE_PROGRESS, builder.build());
// manager.cancel(TYPE_PROGRESS);//設置關閉通知欄
}
}).start();
}
- 使用系統提供的DownloadManager來實現
參考查看
參考鏈接:
基本使用介紹
版本變更以及坑的解決
小圖標灰色問題
基礎知識以及適配