1. 程式人生 > >Android中Notification的framework層講解

Android中Notification的framework層講解

android的notificaiton的聲音sound也是申請的AudioManager機制來播放聲音的。最近讓我找恢復出廠設定後,手機剛啟動,接受簡訊沒有聲音,如果恢復出廠設定後,等一會兒,過個2分鐘再接受簡訊,就有鈴聲了。下面我把我分析程式碼的方法寫下來,給自己和讀者一些啟發:

      日曆也是用的是Notification,但是恢復出廠設定後,立馬設定日曆後,日曆可以出聲音,我看日曆的程式碼,結果發現日曆只是用了Notification的閃屏,真正聲音是日曆自己實現了Mediaplayer來出聲音的。所以我又不得不老老實實地研究Notification.sound到底把聲音傳遞到什麼地方去了?

       首先我在簡訊的com.android.mms.transaction包中的MessagingNotification的573行的java程式碼:notification.sound = TextUtils.isEmpty(ringtoneStr) ? null : Uri.parse(ringtoneStr);打log檢視,發現這個uri確實是存在的,我推測:就是說這個uri傳給了framework一層,但是framework一層有沒有執行完的動作,所以不響。為了驗證是不是簡訊的錯誤,我自己單獨寫了個notification的例子,一個按鈕,點選就發出聲音。這個例子在正常情況下能正常發聲。我就恢復出廠設定後,執行這個例子,結果發現沒有聲音,這就充分驗證了我的猜測。我就去framework去著notificaion.sound = 的聲音傳遞給framework做什麼事情了??

       接著,在Source Insight軟體中匯入framework整個工程,然後搜尋,notificaiton.sounds,結果搜到了,在framework/base/core/java/android/app/Notification.java類。

[java] view plaincopyprint?
  1. /*
  2. * Copyright (C) 2007 The Android Open Source Project
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. *      http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. */
  16. package android.app; 
  17. import java.util.Date; 
  18. import android.app.PendingIntent; 
  19. import android.content.Context; 
  20. import android.content.Intent; 
  21. import android.media.AudioManager; 
  22. import android.net.Uri; 
  23. import android.os.Parcel; 
  24. import android.os.Parcelable; 
  25. import android.text.TextUtils; 
  26. import android.text.format.DateFormat; 
  27. import android.text.format.DateUtils; 
  28. import android.widget.RemoteViews; 
  29. /**
  30. * A class that represents how a persistent notification is to be presented to
  31. * the user using the {@link android.app.NotificationManager}.
  32. *
  33. * <p>For a guide to creating notifications, see the
  34. * <a href="{@docRoot}guide/topics/ui/notifiers/notifications.html">Creating Status
  35. * Bar Notifications</a> document in the Dev Guide.</p>
  36. */
  37. publicclass Notificationimplements Parcelable 
  38. /**
  39.      * Use all default values (where applicable).
  40.      */
  41. publicstaticfinalint DEFAULT_ALL = ~0
  42. /**
  43.      * Use the default notification sound. This will ignore any given
  44.      * {@link #sound}.
  45.      *
  46.      * @see #defaults
  47.      */
  48. publicstaticfinalint DEFAULT_SOUND =1
  49. /**
  50.      * Use the default notification vibrate. This will ignore any given
  51.      * {@link #vibrate}. Using phone vibration requires the
  52.      * {@link android.Manifest.permission#VIBRATE VIBRATE} permission.
  53.      *
  54.      * @see #defaults
  55.      */
  56. public staticfinalint DEFAULT_VIBRATE =2
  57. /**
  58.      * Use the default notification lights. This will ignore the
  59.      * {@link #FLAG_SHOW_LIGHTS} bit, and {@link #ledARGB}, {@link #ledOffMS}, or
  60.      * {@link #ledOnMS}.
  61.      *
  62.      * @see #defaults
  63.      */
  64. publicstaticfinalint DEFAULT_LIGHTS =4
  65. /**
  66.      * The timestamp for the notification.  The icons and expanded views
  67.      * are sorted by this key.
  68.      */
  69. publiclong when; 
  70. /**
  71.      * The resource id of a drawable to use as the icon in the status bar.
  72.      */
  73. public int icon; 
  74. /**
  75.      * The number of events that this notification represents.  For example, in a new mail
  76.      * notification, this could be the number of unread messages.  This number is superimposed over
  77.      * the icon in the status bar.  If the number is 0 or negative, it is not shown in the status
  78.      * bar.
  79.      */
  80. public int number; 
  81. /**
  82.      * The intent to execute when the expanded status entry is clicked.  If
  83.      * this is an activity, it must include the
  84.      * {@link android.content.Intent#FLAG_ACTIVITY_NEW_TASK} flag, which requires
  85.      * that you take care of task management as described in the <em>Activities and Tasks</em>
  86.      * section of the <a href="{@docRoot}guide/topics/fundamentals.html#acttask">Application
  87.      * Fundamentals</a> document.
  88.      */
  89. public PendingIntent contentIntent; 
  90. /**
  91.      * The intent to execute when the status entry is deleted by the user
  92.      * with the "Clear All Notifications" button. This probably shouldn't
  93.      * be launching an activity since several of those will be sent at the
  94.      * same time.
  95.      */
  96. public PendingIntent deleteIntent; 
  97. /**
  98.      * An intent to launch instead of posting the notification to the status bar.
  99.      * Only for use with extremely high-priority notifications demanding the user's
  100.      * <strong>immediate</strong> attention, such as an incoming phone call or
  101.      * alarm clock that the user has explicitly set to a particular time.
  102.      * If this facility is used for something else, please give the user an option
  103.      * to turn it off and use a normal notification, as this can be extremely
  104.      * disruptive.
  105.      */
  106. public PendingIntent fullScreenIntent; 
  107. /**
  108.      * Text to scroll across the screen when this item is added to
  109.      * the status bar.
  110.      */
  111. public CharSequence tickerText; 
  112. /**
  113.      * The view that will represent this notification in the expanded status bar.
  114.      */
  115. public RemoteViews contentView; 
  116. /**
  117.      * If the icon in the status bar is to have more than one level, you can set this.  Otherwise,
  118.      * leave it at its default value of 0.
  119.      *
  120.      * @see android.widget.ImageView#setImageLevel
  121.      * @see android.graphics.drawable#setLevel
  122.      */
  123. publicint iconLevel; 
  124. /**
  125.      * The sound to play.
  126.      *
  127.      * <p>
  128.      * To play the default notification sound, see {@link #defaults}.
  129.      * </p>
  130.      */
  131. public Uri sound; 
  132. /**
  133.      * Use this constant as the value for audioStreamType to request that
  134.      * the default stream type for notifications be used.  Currently the
  135.      * default stream type is STREAM_RING.
  136.      */
  137. publicstaticfinalint STREAM_DEFAULT = -1
  138. /**
  139.      * The audio stream type to use when playing the sound.
  140.      * Should be one of the STREAM_ constants from
  141.      * {@link android.media.AudioManager}.
  142.      */
  143. public int audioStreamType = STREAM_DEFAULT; 
  144. /**
  145.      * The pattern with which to vibrate.
  146.      *
  147.      * <p>
  148.      * To vibrate the default pattern, see {@link #defaults}.
  149.      * </p>
  150.      *
  151.      * @see android.os.Vibrator#vibrate(long[],int)
  152.      */
  153. public long[] vibrate; 
  154. /**
  155.      * The color of the led.  The hardware will do its best approximation.
  156.      *
  157.      * @see #FLAG_SHOW_LIGHTS
  158.      * @see #flags
  159.      */
  160. public int ledARGB; 
  161. /**
  162.      * The number of milliseconds for the LED to be on while it's flashing.
  163.      * The hardware will do its best approximation.
  164.      *
  165.      * @see #FLAG_SHOW_LIGHTS
  166.      * @see #flags
  167.      */
  168. publicint ledOnMS; 
  169. /**
  170.      * The number of milliseconds for the LED to be off while it's flashing.
  171.      * The hardware will do its best approximation.
  172.      *
  173.      * @see #FLAG_SHOW_LIGHTS
  174.      * @see #flags
  175.      */
  176. public int ledOffMS; 
  177. /**
  178.      * Specifies which values should be taken from the defaults.
  179.      * <p>
  180.      * To set, OR the desired from {@link #DEFAULT_SOUND},
  181.      * {@link #DEFAULT_VIBRATE}, {@link #DEFAULT_LIGHTS}. For all default
  182.      * values, use {@link #DEFAULT_ALL}.
  183.      * </p>
  184.      */
  185. public int defaults; 
  186. /**
  187.      * Bit to be bitwise-ored into the {@link #flags} field that should be
  188.      * set if you want the LED on for this notification.
  189.      * <ul>
  190.      * <li>To turn the LED off, pass 0 in the alpha channel for colorARGB
  191.      *      or 0 for both ledOnMS and ledOffMS.</li>
  192.      * <li>To turn the LED on, pass 1 for ledOnMS and 0 for ledOffMS.</li>
  193.      * <li>To flash the LED, pass the number of milliseconds that it should
  194.      *      be on and off to ledOnMS and ledOffMS.</li>
  195.      * </ul>
  196.      * <p>
  197.      * Since hardware varies, you are not guaranteed that any of the values
  198.      * you pass are honored exactly.  Use the system defaults (TODO) if possible
  199.      * because they will be set to values that work on any given hardware.
  200.      * <p>
  201.      * The alpha channel must be set for forward compatibility.
  202.      *
  203.      */
  204. publicstaticfinalint FLAG_SHOW_LIGHTS        =0x00000001
  205. /**
  206.      * Bit to be bitwise-ored into the {@link #flags} field that should be
  207.      * set if this notification is in reference to something that is ongoing,
  208.      * like a phone call.  It should not be set if this notification is in
  209.      * reference to something that happened at a particular point in time,
  210.      * like a missed phone call.
  211.      */
  212. public staticfinalint FLAG_ONGOING_EVENT      =0x00000002
  213. /**
  214.      * Bit to be bitwise-ored into the {@link #flags} field that if set,
  215.      * the audio will be repeated until the notification is
  216.      * cancelled or the notification window is opened.
  217.      */
  218. publicstaticfinalint FLAG_INSISTENT          =0x00000004
  219. /**
  220.      * Bit to be bitwise-ored into the {@link #flags} field that should be
  221.      * set if you want the sound and/or vibration play each time the
  222.      * notification is sent, even if it has not been canceled before that.
  223.      */
  224. public staticfinalint FLAG_ONLY_ALERT_ONCE    =0x00000008
  225. /**
  226.      * Bit to be bitwise-ored into the {@link #flags} field that should be
  227.      * set if the notification should be canceled when it is clicked by the
  228.      * user.
  229.      */
  230. publicstaticfinalint FLAG_AUTO_CANCEL        =0x00000010
  231. /**
  232.      * Bit to be bitwise-ored into the {@link #flags} field that should be
  233.      * set if the notification should not be canceled when the user clicks
  234.      * the Clear all button.
  235.      */
  236. public staticfinalint FLAG_NO_CLEAR           =0x00000020
  237. /**
  238.      * Bit to be bitwise-ored into the {@link #flags} field that should be
  239.      * set if this notification represents a currently running service.  This
  240.      * will normally be set for you by {@link Service#startForeground}.
  241.      */
  242. publicstaticfinalint FLAG_FOREGROUND_SERVICE =0x00000040
  243. publicint flags; 
  244. /**
  245.      * Constructs a Notification object with everything set to 0.
  246.      */
  247. public Notification() 
  248.     { 
  249. this.when = System.currentTimeMillis(); 
  250.     } 
  251. /**
  252.      * @deprecated use {@link #Notification(int,CharSequence,long)} and {@link #setLatestEventInfo}.
  253.      * @hide
  254.      */
  255. public Notification(Context context,int icon, CharSequence tickerText,long when, 
  256.             CharSequence contentTitle, CharSequence contentText, Intent contentIntent) 
  257.     { 
  258. this.when = when; 
  259. this.icon = icon; 
  260. this.tickerText = tickerText; 
  261.         setLatestEventInfo(context, contentTitle, contentText, 
  262.                 PendingIntent.getActivity(context, 0, contentIntent,0)); 
  263.     } 
  264. /**
  265.      * Constructs a Notification object with the information needed to
  266.      * have a status bar icon without the standard expanded view.
  267.      *
  268.      * @param icon          The resource id of the icon to put in the status bar.
  269.      * @param tickerText    The text that flows by in the status bar when the notification first
  270.      *                      activates.
  271.      * @param when          The time to show in the time field.  In the System.currentTimeMillis
  272.      *                      timebase.
  273.      */
  274. public Notification(int icon, CharSequence tickerText,long when) 
  275.     { 
  276. this.icon = icon; 
  277. this.tickerText = tickerText; 
  278. this.when = when; 
  279.     } 
  280. /**
  281.      * Unflatten the notification from a parcel.
  282.      */
  283. public Notification(Parcel parcel) 
  284.     { 
  285. int version = parcel.readInt(); 
  286.         when = parcel.readLong(); 
  287.         icon = parcel.readInt(); 
  288.         number = parcel.readInt(); 
  289. if (parcel.readInt() !=0) { 
  290.             contentIntent = PendingIntent.CREATOR.createFromParcel(parcel); 
  291.         } 
  292. if (parcel.readInt() !=0) { 
  293.             deleteIntent = PendingIntent.CREATOR.createFromParcel(parcel); 
  294.         } 
  295. if (parcel.readInt() !=0) { 
  296.             tickerText = TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(parcel); 
  297.         } 
  298. if (parcel.readInt() !=0) { 
  299.             contentView = RemoteViews.CREATOR.createFromParcel(parcel); 
  300.         } 
  301.         defaults = parcel.readInt(); 
  302.         flags = parcel.readInt(); 
  303. if (parcel.readInt() !=0) { 
  304.             sound = Uri.CREATOR.createFromParcel(parcel); 
  305.         } 
  306.         audioStreamType = parcel.readInt(); 
  307.         vibrate = parcel.createLongArray(); 
  308.         ledARGB = parcel.readInt(); 
  309.         ledOnMS = parcel.readInt(); 
  310.         ledOffMS = parcel.readInt(); 
  311.         iconLevel = parcel.readInt(); 
  312. if (parcel.readInt() !=0) { 
  313.             fullScreenIntent = PendingIntent.CREATOR.createFromParcel(parcel); 
  314.         } 
  315.     } 
  316. public Notification clone() { 
  317.         Notification that = new Notification(); 
  318.         that.when = this.when; 
  319.         that.icon = this.icon; 
  320.         that.number = this.number; 
  321. // PendingIntents are global, so there's no reason (or way) to clone them.
  322.         that.contentIntent = this.contentIntent; 
  323.         that.deleteIntent = this.deleteIntent; 
  324.         that.fullScreenIntent = this.fullScreenIntent; 
  325. if (this.tickerText !=null) { 
  326.             that.tickerText = this.tickerText.toString(); 
  327.         } 
  328. if (this.contentView !=null) { 
  329.             that.contentView = this.contentView.clone(); 
  330.         } 
  331.         that.iconLevel = that.iconLevel; 
  332.         that.sound = this.sound;// android.net.Uri is immutable
  333.         that.audioStreamType = this.audioStreamType; 
  334. final long[] vibrate = this.vibrate; 
  335. if (vibrate != null) { 
  336. finalint N = vibrate.length; 
  337. finallong[] vib = that.vibrate =newlong[N]; 
  338.             System.arraycopy(vibrate, 0, vib,0, N); 
  339.         } 
  340.         that.ledARGB = this.ledARGB; 
  341.         that.ledOnMS = this.ledOnMS; 
  342.         that.ledOffMS = this.ledOffMS; 
  343.         that.defaults = this.defaults; 
  344.         that.flags = this.flags; 
  345. return that; 
  346.     } 
  347. publicint describeContents() { 
  348. return 0
  349.     } 
  350. /**
  351.      * Flatten this notification from a parcel.
  352.      */
  353. public void writeToParcel(Parcel parcel, int flags) 
  354.     { 
  355.         parcel.writeInt(1); 
  356.         parcel.writeLong(when); 
  357.         parcel.writeInt(icon); 
  358.         parcel.writeInt(number); 
  359. if (contentIntent != null) { 
  360.             parcel.writeInt(1); 
  361.             contentIntent.writeToParcel(parcel, 0); 
  362.         } else
  363.             parcel.writeInt(0); 
  364.         } 
  365. if (deleteIntent != null) { 
  366.             parcel.writeInt(1); 
  367.             deleteIntent.writeToParcel(parcel, 0); 
  368.         } else
  369.             parcel.writeInt(0); 
  370.         } 
  371. if (tickerText != null) { 
  372.             parcel.writeInt(1); 
  373.             TextUtils.writeToParcel(tickerText, parcel, flags); 
  374.         } else
  375.             parcel.writeInt(0); 
  376.         } 
  377. if (contentView != null) { 
  378.             parcel.writeInt(1); 
  379.             contentView.writeToParcel(parcel, 0); 
  380.         } else
  381.             parcel.writeInt(0); 
  382.         } 
  383.         parcel.writeInt(defaults); 
  384.         parcel.writeInt(this.flags); 
  385. if (sound != null) { 
  386.             parcel.writeInt(1); 
  387.             sound.writeToParcel(parcel, 0); 
  388.         } else
  389.             parcel.writeInt(0); 
  390.         } 
  391.         parcel.writeInt(audioStreamType); 
  392.         parcel.writeLongArray(vibrate); 
  393.         parcel.writeInt(ledARGB); 
  394.         parcel.writeInt(ledOnMS); 
  395.         parcel.writeInt(ledOffMS); 
  396.         parcel.writeInt(iconLevel); 
  397. if (fullScreenIntent !=null) { 
  398.             parcel.writeInt(1); 
  399.             fullScreenIntent.writeToParcel(parcel, 0); 
  400.         } else
  401.             parcel.writeInt(0); 
  402.         } 
  403.     } 
  404. /**
  405.      * Parcelable.Creator that instantiates Notification objects
  406.      */
  407. publicstaticfinal Parcelable.Creator<Notification> CREATOR 
  408.             = new Parcelable.Creator<Notification>() 
  409.     { 
  410. public Notification createFromParcel(Parcel parcel) 
  411.         { 
  412. returnnew Notification(parcel); 
  413.         } 
  414. public Notification[] newArray(int size) 
  415.         { 
  416. returnnew Notification[size]; 
  417.         } 
  418.     }; 
  419. /**
  420.      * Sets the {@link #contentView} field to be a view with the standard "Latest Event"
  421.      * layout.
  422.      *
  423.      * <p>Uses the {@link #icon} and {@link #when} fields to set the icon and time fields
  424.      * in the view.</p>
  425.      * @param context       The context for your application / activity.
  426.      * @param contentTitle The title that goes in the expanded entry.
  427.      * @param contentText  The text that goes in the expanded entry.
  428.      * @param contentIntent The intent to launch when the user clicks the expanded notification.
  429.      * If this is an activity, it must include the
  430.      * {@link android.content.Intent#FLAG_ACTIVITY_NEW_TASK} flag, which requires
  431.      * that you take care of task management as described in
  432.      * <a href="{@docRoot}guide/topics/fundamentals.html#lcycles">Application Fundamentals: Activities and Tasks</a>.
  433.      */
  434. public void setLatestEventInfo(Context context, 
  435.             CharSequence contentTitle, CharSequence contentText, PendingIntent contentIntent) { 
  436.         RemoteViews contentView = new RemoteViews(context.getPackageName(), 
  437.                 com.android.internal.R.layout.status_bar_latest_event_content); 
  438. if (this.icon !=0) { 
  439.             contentView.setImageViewResource(com.android.internal.R.id.icon,this.icon); 
  440.         } 
  441. if (contentTitle != null) { 
  442.             contentView.setTextViewText(com.android.internal.R.id.title, contentTitle); 
  443.         } 
  444. if (contentText !=null) { 
  445.             contentView.setTextViewText(com.android.internal.R.id.text, contentText); 
  446.         } 
  447. if (this.when !=0) { 
  448.             contentView.setLong(com.android.internal.R.id.time,"setTime", when); 
  449.         } 
  450. this.contentView = contentView; 
  451. this.contentIntent = contentIntent; 
  452.     } 
  453. @Override
  454. public String toString() { 
  455.         StringBuilder sb = new StringBuilder(); 
  456.         sb.append("Notification(vibrate="); 
  457. if (this.vibrate !=null) { 
  458. int N =this.vibrate.length-1
  459.             sb.append("["); 
  460. for (int i=0; i<N; i++) { 
  461.                 sb.append(this.vibrate[i]); 
  462.                 sb.append(','); 
  463.             } 
  464. if (N != -1) { 
  465.                 sb.append(this.vibrate[N]); 
  466.             } 
  467.             sb.append("]"); 
  468.         } else if ((this.defaults & DEFAULT_VIBRATE) !=0) { 
  469.             sb.append("default"); 
  470.         } else
  471.             sb.append("null"); 
  472.         } 
  473.         sb.append(",sound="); 
  474. if (this.sound !=null) { 
  475.             sb.append(this.sound.toString()); 
  476.         } else if ((this.defaults & DEFAULT_SOUND) !=0) { 
  477.             sb.append("default"); 
  478.         } else
  479.             sb.append("null"); 
  480.         } 
  481.         sb.append(",defaults=0x"); 
  482.         sb.append(Integer.toHexString(this.defaults)); 
  483.         sb.append(",flags=0x"); 
  484.         sb.append(Integer.toHexString(this.flags)); 
  485.         sb.append(")"); 
  486. return sb.toString(); 
  487.     } 
[java] view plaincopyprint?
  1. /*
  2. * Copyright (C) 2007 The Android Open Source Project
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. *      http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. */
  16. package android.app; 
  17. import java.util.Date; 
  18. import android.app.PendingIntent; 
  19. import android.content.Context; 
  20. import android.content.Intent; 
  21. import android.media.AudioManager; 
  22. import android.net.Uri; 
  23. import android.os.Parcel; 
  24. import android.os.Parcelable; 
  25. import android.text.TextUtils; 
  26. import android.text.format.DateFormat; 
  27. import android.text.format.DateUtils; 
  28. import android.widget.RemoteViews; 
  29. /**
  30. * A class that represents how a persistent notification is to be presented to
  31. * the user using the {@link android.app.NotificationManager}.
  32. *
  33. * <p>For a guide to creating notifications, see the
  34. * <a href="{@docRoot}guide/topics/ui/notifiers/notifications.html">Creating Status
  35. * Bar Notifications</a> document in the Dev Guide.</p>
  36. */
  37. publicclass Notificationimplements Parcelable 
  38.     /**
  39.      * Use all default values (where applicable).
  40.      */
  41.     publicstaticfinalint DEFAULT_ALL = ~0
  42.     /**
  43.      * Use the default notification sound. This will ignore any given
  44.      * {@link #sound}.
  45.      *
  46.      * @see #defaults
  47.      */
  48.     publicstaticfinalint DEFAULT_SOUND =1
  49.     /**
  50.      * Use the default notification vibrate. This will ignore any given
  51.      * {@link #vibrate}. Using phone vibration requires the
  52.      * {@link android.Manifest.permission#VIBRATE VIBRATE} permission.
  53.      *
  54.      * @see #defaults
  55.      */
  56.     publicstaticfinalint DEFAULT_VIBRATE =2
  57.     /**
  58.      * Use the default notification lights. This will ignore the
  59.      * {@link #FLAG_SHOW_LIGHTS} bit, and {@link #ledARGB}, {@link #ledOffMS}, or
  60.      * {@link #ledOnMS}.
  61.      *
  62.      * @see #defaults
  63.      */
  64.     publicstaticfinalint DEFAULT_LIGHTS =4
  65.     /**
  66.      * The timestamp for the notification.  The icons and expanded views
  67.      * are sorted by this key.
  68.      */
  69.     publiclong when; 
  70.     /**
  71.      * The resource id of a drawable to use as the icon in the status bar.
  72.      */
  73.     publicint icon; 
  74.     /**
  75.      * The number of events that this notification represents.  For example, in a new mail
  76.      * notification, this could be the number of unread messages.  This number is superimposed over
  77.      * the icon in the status bar.  If the number is 0 or negative, it is not shown in the status
  78.      * bar.
  79.      */
  80.     publicint number; 
  81.     /**
  82.      * The intent to execute when the expanded status entry is clicked.  If
  83.      * this is an activity, it must include the
  84.      * {@link android.content.Intent#FLAG_ACTIVITY_NEW_TASK} flag, which requires
  85.      * that you take care of task management as described in the <em>Activities and Tasks</em>
  86.      * section of the <a href="{@docRoot}guide/topics/fundamentals.html#acttask">Application
  87.      * Fundamentals</a> document.
  88.      */
  89.     public PendingIntent contentIntent; 
  90.     /**
  91.      * The intent to execute when the status entry is deleted by the user
  92.      * with the "Clear All Notifications" button. This probably shouldn't
  93.      * be launching an activity since several of those will be sent at the
  94.      * same time.
  95.      */
  96.     public PendingIntent deleteIntent; 
  97.     /**
  98.      * An intent to launch instead of posting the notification to the status bar.
  99.      * Only for use with extremely high-priority notifications demanding the user's
  100.      * <strong>immediate</strong> attention, such as an incoming phone call or
  101.      * alarm clock that the user has explicitly set to a particular time.
  102.      * If this facility is used for something else, please give the user an option
  103.      * to turn it off and use a normal notification, as this can be extremely
  104.      * disruptive.
  105.      */
  106.     public PendingIntent fullScreenIntent; 
  107.     /**
  108.      * Text to scroll across the screen when this item is added to