Optimizations in the notification list:

    - sort notifications by timestamp
	- deal with notification bursts better by waiting to
	  refresh the list until things settle down

Change-Id: Ie41051afcb0a7a917f2a97a3311628b34626c125
diff --git a/src/com/android/settings/NotificationStation.java b/src/com/android/settings/NotificationStation.java
index 5fa3724..1fdbcab 100644
--- a/src/com/android/settings/NotificationStation.java
+++ b/src/com/android/settings/NotificationStation.java
@@ -30,6 +30,7 @@
 import android.graphics.drawable.Drawable;
 import android.net.Uri;
 import android.os.Bundle;
+import android.os.Handler;
 import android.os.RemoteException;
 import android.os.ServiceManager;
 import android.os.UserHandle;
@@ -46,6 +47,7 @@
 import com.android.internal.statusbar.StatusBarNotification;
 
 import java.util.ArrayList;
+import java.util.Comparator;
 import java.util.List;
 
 public class NotificationStation extends SettingsPreferenceFragment {
@@ -57,23 +59,43 @@
     private final PackageReceiver mPackageReceiver = new PackageReceiver();
 
     private INotificationManager mNoMan;
+
+    private Runnable mRefreshListRunnable = new Runnable() {
+        @Override
+        public void run() {
+            refreshList();
+        }
+    };
+
     private INotificationListener.Stub mListener = new INotificationListener.Stub() {
         @Override
         public void onNotificationPosted(StatusBarNotification notification) throws RemoteException {
             Log.v(TAG, "onNotificationPosted: " + notification);
-            getListView().post(new Runnable() { public void run() { refreshList(); }});
+            final Handler h = getListView().getHandler();
+            h.removeCallbacks(mRefreshListRunnable);
+            h.postDelayed(mRefreshListRunnable, 100);
         }
 
         @Override
         public void onNotificationRemoved(StatusBarNotification notification) throws RemoteException {
-            Log.v(TAG, "onNotificationRemoved: " + notification);
-            getListView().post(new Runnable() { public void run() { refreshList(); }});
+            final Handler h = getListView().getHandler();
+            h.removeCallbacks(mRefreshListRunnable);
+            h.postDelayed(mRefreshListRunnable, 100);
         }
     };
 
     private NotificationHistoryAdapter mAdapter;
     private Context mContext;
 
+    private final Comparator<HistoricalNotificationInfo> mNotificationSorter
+            = new Comparator<HistoricalNotificationInfo>() {
+                @Override
+                public int compare(HistoricalNotificationInfo lhs,
+                                   HistoricalNotificationInfo rhs) {
+                    return (int)(rhs.timestamp - lhs.timestamp);
+                }
+            };
+
     @Override
     public void onAttach(Activity activity) {
         logd("onAttach(%s)", activity.getClass().getSimpleName());
@@ -146,6 +168,7 @@
             logd("adding %d infos", infos.size());
             mAdapter.clear();
             mAdapter.addAll(infos);
+            mAdapter.sort(mNotificationSorter);
         }
     }