Notification之----Android5.0實(shí)現(xiàn)原理(一)

概述

寫(xiě)這篇文章的起因是當(dāng)我自定義通知欄樣式時(shí)色冀,設(shè)置的view高度最終只能顯示為通知欄的默認(rèn)高度(64dp)潭袱,讓人十分困惑,于是研究了下源碼呐伞。
除了解開(kāi)真相意外敌卓,還了解到了包括bigview,pengdingintent的點(diǎn)擊事件伶氢,通知欄限制等知識(shí)點(diǎn),收獲頗多瘪吏,在這里分享給大家癣防。希望能讓大家明白一個(gè)通知是如何添加到狀態(tài)欄上面去的,如果遇到奇怪的問(wèn)題不至于抓瞎掌眠。

前提

本文是以android5.0的源碼為基礎(chǔ)的并且假設(shè)大家都知道notification的基本用法蕾盯。

構(gòu)造通知

在我們使用NotificationCompat.Builder對(duì)象設(shè)置完各種參數(shù)(小/大圖標(biāo),標(biāo)題蓝丙,內(nèi)容等)后级遭,最后會(huì)調(diào)用build方法來(lái)得到一個(gè)Notification望拖,然后使用NotificationManager來(lái)發(fā)出通知。我們就先來(lái)看看build方法做了什么事挫鸽。
NotificationCompat是v4包中的一個(gè)類(lèi)说敏,做了android各個(gè)版本的兼容,但是不論是哪個(gè)版本丢郊,最后build方法都是調(diào)用的Notification的build方法盔沫,所以我們直接看Notification的build方法。
frameworks/base/core/java/android/app/Notification.java

/**
 * Combine all of the options that have been set and return a new {@link Notification}
 * object.
 */
public Notification build() {
    ... 
    //設(shè)置通知的默認(rèn)信息
    Notification n = buildUnstyled();

   //設(shè)置通知的樣式信息
    if (mStyle != null) {
        n = mStyle.buildStyled(n);
    }
    ...
    return n;
}

方法的注釋說(shuō)得很清楚了枫匾,就是將所有的設(shè)置選項(xiàng)聯(lián)合在一起返回一個(gè)新的通知架诞。

buildUnstyled

其中buildUnstyled()所說(shuō)的默認(rèn)信息就是在android4.0以前還不能展開(kāi)的時(shí)候所包括的所有信息,包括大/小圖標(biāo)干茉,時(shí)間谴忧,標(biāo)題,內(nèi)容角虫,自定義view等信息沾谓。

/**
 * Apply the unstyled operations and return a new {@link Notification} object.
 * @hide
 */
public Notification buildUnstyled() {
    Notification n = new Notification();
    n.when = mWhen;
    n.icon = mSmallIcon;
    ...
    setBuilderContentView(n, makeContentView());
    n.contentIntent = mContentIntent;
    ...
    setBuilderBigContentView(n, makeBigContentView());
    setBuilderHeadsUpContentView(n, makeHeadsUpContentView());
    // Note: If you're adding new fields, also update restoreFromNotitification().
    return n;
}

setBuilderContentView用于設(shè)置通知欄的ContentView屬性

private void setBuilderContentView(Notification n, RemoteViews contentView) {
    n.contentView = contentView;
    ...
}

makeContentView()是構(gòu)造出所需要填充的view

private RemoteViews makeContentView() {
    if (mContentView != null) {
        return mContentView;
    } else {
        return applyStandardTemplate(getBaseLayoutResource());
    }
}

如果你沒(méi)有使用自定view,將會(huì)使用標(biāo)準(zhǔn)的模板樣式

private int getBaseLayoutResource() {
     return R.layout.notification_template_material_base;
}

這里只講了setBuilderContentView(n, makeContentView());方法上遥, 后面的setBuilderBigContentView(n, makeBigContentView());setBuilderHeadsUpContentView(n, makeHeadsUpContentView());方法與其類(lèi)似都是設(shè)置通知的相應(yīng)屬性搏屑,直接給出結(jié)果,不再累述
<pre>
setBuilderHeadsUpContentView --> n.headsUpContentView
setBuilderBigContentView --> n.bigContentView = bigContentView;
</pre>

這樣粉楚,通知的顯示內(nèi)容就已經(jīng)構(gòu)造好了辣恋。

1 .可以看出,在構(gòu)造階段模软,并沒(méi)有對(duì)通知欄的自定義view高度做出限制伟骨,但最后顯示的時(shí)候卻是一個(gè)固定高度,why?
2.先記住這里的bigContentView屬性燃异,后面會(huì)在提到携狭。

buildStyled

4.0后如果設(shè)置了BigText,BigPic等樣式回俐,則會(huì)調(diào)用buildStyled方法逛腿。buildStyled是Notification.Style中的一個(gè)方法

public Notification buildStyled(Notification wip) {
    ...
    populateBigContentView(wip);
    ...
    return wip;
}

populateBigContentView是一個(gè)protected所修飾的方法,具體的實(shí)現(xiàn)是在所設(shè)置的Style中仅颇,這里里BigPic Style為例单默,在BigPictureStyle類(lèi)中,重寫(xiě)了該方法

@Override
public void populateBigContentView(Notification wip) {
    mBuilder.setBuilderBigContentView(wip, makeBigContentView());
}
private RemoteViews makeBigContentView() {
    RemoteViews contentView = getStandardView(mBuilder.getBigPictureLayoutResource());
    contentView.setImageViewBitmap(R.id.big_picture, mPicture);
    ...
    return contentView;
}
private int getBigPictureLayoutResource() {
    return R.layout.notification_template_material_big_picture;
}

如果是BigPic Style樣式的通知忘瓦,其實(shí)也是調(diào)用了系統(tǒng)中設(shè)置的一個(gè)模板布局notification_template_material_big_picture.
這里又調(diào)用了一次mBuilder.setBuilderBigContentView搁廓,前面提到了該方法是給notification的bigContentView的屬性賦值。所以如果設(shè)置了樣式,則會(huì)覆蓋默認(rèn)的bigContentView值

總結(jié)

在通知構(gòu)造環(huán)節(jié)境蜕,我們需要記住做了最重要的2件事

  1. 給Notification的contentView屬性賦值蝙场,該值可以是自定義的view也可以是系統(tǒng)默認(rèn)樣式的view
  2. 給Notification的bigContentView屬性賦值,該值可以使自定義的view也可以是系統(tǒng)默認(rèn)樣式的view

相關(guān)閱讀

Notification之---NotificationListenerService5.0實(shí)現(xiàn)原理
Notification之----Android5.0實(shí)現(xiàn)原理(二)
Notification之----自定義樣式
Notification之----默認(rèn)樣式
Notification之----任務(wù)棧

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末粱年,一起剝皮案震驚了整個(gè)濱河市售滤,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌逼泣,老刑警劉巖趴泌,帶你破解...
    沈念sama閱讀 211,123評(píng)論 6 490
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異拉庶,居然都是意外死亡嗜憔,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,031評(píng)論 2 384
  • 文/潘曉璐 我一進(jìn)店門(mén)氏仗,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)吉捶,“玉大人,你說(shuō)我怎么就攤上這事皆尔∧盘颍” “怎么了?”我有些...
    開(kāi)封第一講書(shū)人閱讀 156,723評(píng)論 0 345
  • 文/不壞的土叔 我叫張陵慷蠕,是天一觀(guān)的道長(zhǎng)珊拼。 經(jīng)常有香客問(wèn)我,道長(zhǎng)流炕,這世上最難降的妖魔是什么澎现? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 56,357評(píng)論 1 283
  • 正文 為了忘掉前任,我火速辦了婚禮每辟,結(jié)果婚禮上剑辫,老公的妹妹穿的比我還像新娘。我一直安慰自己渠欺,他們只是感情好妹蔽,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,412評(píng)論 5 384
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著挠将,像睡著了一般胳岂。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上舔稀,一...
    開(kāi)封第一講書(shū)人閱讀 49,760評(píng)論 1 289
  • 那天旦万,我揣著相機(jī)與錄音,去河邊找鬼镶蹋。 笑死,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的贺归。 我是一名探鬼主播淆两,決...
    沈念sama閱讀 38,904評(píng)論 3 405
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼拂酣!你這毒婦竟也來(lái)了秋冰?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 37,672評(píng)論 0 266
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤婶熬,失蹤者是張志新(化名)和其女友劉穎剑勾,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體赵颅,經(jīng)...
    沈念sama閱讀 44,118評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡虽另,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,456評(píng)論 2 325
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了饺谬。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片捂刺。...
    茶點(diǎn)故事閱讀 38,599評(píng)論 1 340
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖募寨,靈堂內(nèi)的尸體忽然破棺而出族展,到底是詐尸還是另有隱情,我是刑警寧澤拔鹰,帶...
    沈念sama閱讀 34,264評(píng)論 4 328
  • 正文 年R本政府宣布仪缸,位于F島的核電站,受9級(jí)特大地震影響列肢,放射性物質(zhì)發(fā)生泄漏恰画。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,857評(píng)論 3 312
  • 文/蒙蒙 一例书、第九天 我趴在偏房一處隱蔽的房頂上張望锣尉。 院中可真熱鬧,春花似錦决采、人聲如沸自沧。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 30,731評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)拇厢。三九已至,卻和暖如春晒喷,著一層夾襖步出監(jiān)牢的瞬間孝偎,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 31,956評(píng)論 1 264
  • 我被黑心中介騙來(lái)泰國(guó)打工凉敲, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留衣盾,地道東北人寺旺。 一個(gè)月前我還...
    沈念sama閱讀 46,286評(píng)論 2 360
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像势决,于是被迫代替她去往敵國(guó)和親阻塑。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,465評(píng)論 2 348

推薦閱讀更多精彩內(nèi)容

  • 原文出處: http://www.androidchina.net/6174.html Notification在...
    木木00閱讀 12,304評(píng)論 3 32
  • Android 自定義View的各種姿勢(shì)1 Activity的顯示之ViewRootImpl詳解 Activity...
    passiontim閱讀 171,744評(píng)論 25 707
  • 轉(zhuǎn)載自:http://blog.csdn.net/vipzjyno1/article/details/252480...
    HEXG_閱讀 5,809評(píng)論 0 2
  • 發(fā)現(xiàn) 關(guān)注 消息 iOS 第三方庫(kù)果复、插件陈莽、知名博客總結(jié) 作者大灰狼的小綿羊哥哥關(guān)注 2017.06.26 09:4...
    肇東周閱讀 12,059評(píng)論 4 62
  • 1、了解進(jìn)程與線(xiàn)程的概念虽抄。 (1)進(jìn)程就是一個(gè)正在執(zhí)行中的程序(例如:qq)走搁。 (2)每一個(gè)進(jìn)程執(zhí)行都有一個(gè)執(zhí)行順...
    周周楊楊閱讀 286評(píng)論 0 1