diff --git a/src/com/android/settings/CancellablePreference.java b/src/com/android/settings/CancellablePreference.java
new file mode 100644
index 0000000..ab723ca
--- /dev/null
+++ b/src/com/android/settings/CancellablePreference.java
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2015 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.settings;
+
+import android.content.Context;
+import android.preference.Preference;
+import android.util.AttributeSet;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.widget.ImageView;
+
+public class CancellablePreference extends Preference implements OnClickListener {
+
+    private boolean mCancellable;
+    private OnCancelListener mListener;
+
+    public CancellablePreference(Context context) {
+        super(context);
+        setWidgetLayoutResource(R.layout.cancel_pref_widget);
+    }
+
+    public CancellablePreference(Context context, AttributeSet attrs) {
+        super(context, attrs);
+        setWidgetLayoutResource(R.layout.cancel_pref_widget);
+    }
+
+    public void setCancellable(boolean isCancellable) {
+        mCancellable = isCancellable;
+        notifyChanged();
+    }
+
+    public void setOnCancelListener(OnCancelListener listener) {
+        mListener = listener;
+    }
+
+    @Override
+    protected void onBindView(View view) {
+        super.onBindView(view);
+
+        ImageView cancel = (ImageView) view.findViewById(R.id.cancel);
+        cancel.setVisibility(mCancellable ? View.VISIBLE : View.INVISIBLE);
+        cancel.setOnClickListener(this);
+    }
+
+    @Override
+    public void onClick(View v) {
+        if (mListener != null) {
+            mListener.onCancel(this);
+        }
+    }
+
+    public interface OnCancelListener {
+        void onCancel(CancellablePreference preference);
+    }
+
+}
diff --git a/src/com/android/settings/DevelopmentSettings.java b/src/com/android/settings/DevelopmentSettings.java
index 5c7e0e9..6c2f135 100644
--- a/src/com/android/settings/DevelopmentSettings.java
+++ b/src/com/android/settings/DevelopmentSettings.java
@@ -164,8 +164,6 @@
 
     private static final String SHOW_ALL_ANRS_KEY = "show_all_anrs";
 
-    private static final String PROCESS_STATS = "proc_stats";
-
     private static final String PACKAGE_MIME_TYPE = "application/vnd.android.package-archive";
 
     private static final String TERMINAL_APP_PACKAGE = "com.android.terminal";
@@ -246,7 +244,6 @@
 
     private SwitchPreference mShowAllANRs;
 
-    private PreferenceScreen mProcessStats;
     private final ArrayList<Preference> mAllPrefs = new ArrayList<Preference>();
 
     private final ArrayList<SwitchPreference> mResetSwitchPrefs
@@ -397,9 +394,6 @@
             mAllPrefs.add(hdcpChecking);
             removePreferenceForProduction(hdcpChecking);
         }
-
-        mProcessStats = (PreferenceScreen) findPreference(PROCESS_STATS);
-        mAllPrefs.add(mProcessStats);
     }
 
     private ListPreference addListPreference(String prefKey) {
diff --git a/src/com/android/settings/SettingsActivity.java b/src/com/android/settings/SettingsActivity.java
index caf2491..ee2b1b4 100644
--- a/src/com/android/settings/SettingsActivity.java
+++ b/src/com/android/settings/SettingsActivity.java
@@ -340,6 +340,7 @@
             ZenModePrioritySettings.class.getName(),
             ZenModeScheduleRuleSettings.class.getName(),
             ZenModeExternalRuleSettings.class.getName(),
+            ProcessStatsUi.class.getName(),
     };
 
 
diff --git a/src/com/android/settings/applications/ProcStatsData.java b/src/com/android/settings/applications/ProcStatsData.java
new file mode 100644
index 0000000..1e32cc9
--- /dev/null
+++ b/src/com/android/settings/applications/ProcStatsData.java
@@ -0,0 +1,408 @@
+/*
+ * Copyright (C) 2015 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.settings.applications;
+
+import android.app.ActivityManager;
+import android.content.Context;
+import android.content.pm.PackageManager;
+import android.os.ParcelFileDescriptor;
+import android.os.RemoteException;
+import android.os.ServiceManager;
+import android.os.SystemClock;
+import android.text.format.Formatter;
+import android.util.ArrayMap;
+import android.util.Log;
+import android.util.SparseArray;
+
+import com.android.internal.app.IProcessStats;
+import com.android.internal.app.ProcessMap;
+import com.android.internal.app.ProcessStats;
+import com.android.internal.app.ProcessStats.ProcessDataCollection;
+import com.android.internal.app.ProcessStats.TotalMemoryUseCollection;
+import com.android.internal.util.MemInfoReader;
+import com.android.settings.R;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.ArrayList;
+import java.util.Comparator;
+import java.util.List;
+
+public class ProcStatsData {
+
+    private static final String TAG = "ProcStatsManager";
+
+    private static final boolean DEBUG = ProcessStatsUi.DEBUG;
+
+    private static ProcessStats sStatsXfer;
+
+    private PackageManager mPm;
+    private Context mContext;
+    private long memTotalTime;
+
+    private IProcessStats mProcessStats;
+    private ProcessStats mStats;
+
+    private int mMemState;
+
+    private boolean mUseUss;
+    private long mDuration;
+
+    private int[] mMemStates;
+
+    private int[] mStates;
+
+    private MemInfo mMemInfo;
+
+    private ArrayList<ProcStatsPackageEntry> pkgEntries;
+
+    public ProcStatsData(Context context, boolean useXfer) {
+        mContext = context;
+        mPm = context.getPackageManager();
+        mProcessStats = IProcessStats.Stub.asInterface(
+                ServiceManager.getService(ProcessStats.SERVICE_NAME));
+        mMemStates = ProcessStats.ALL_MEM_ADJ;
+        mStates = ProcessStats.BACKGROUND_PROC_STATES;
+        if (useXfer) {
+            mStats = sStatsXfer;
+        }
+    }
+
+    public void setTotalTime(int totalTime) {
+        memTotalTime = totalTime;
+    }
+
+    public void xferStats() {
+        sStatsXfer = mStats;
+    }
+
+    public void setMemStates(int[] memStates) {
+        mMemStates = memStates;
+        refreshStats(false);
+    }
+
+    public void setStats(int[] stats) {
+        this.mStates = stats;
+        refreshStats(false);
+    }
+
+    public int getMemState() {
+        return mMemState;
+    }
+
+    public MemInfo getMemInfo() {
+        return mMemInfo;
+    }
+
+    public long getElapsedTime() {
+        return mStats.mTimePeriodEndRealtime - mStats.mTimePeriodStartRealtime;
+    }
+
+    public void setDuration(long duration) {
+        if (duration != mDuration) {
+            mDuration = duration;
+            refreshStats(true);
+        }
+    }
+
+    public long getDuration() {
+        return mDuration;
+    }
+
+    public List<ProcStatsPackageEntry> getEntries() {
+        return pkgEntries;
+    }
+
+    public void refreshStats(boolean forceLoad) {
+        if (mStats == null || forceLoad) {
+            load();
+        }
+
+        pkgEntries = new ArrayList<>();
+
+        long now = SystemClock.uptimeMillis();
+
+        memTotalTime = ProcessStats.dumpSingleTime(null, null, mStats.mMemFactorDurations,
+                mStats.mMemFactor, mStats.mStartTime, now);
+
+        ProcessStats.TotalMemoryUseCollection totalMem = new ProcessStats.TotalMemoryUseCollection(
+                ProcessStats.ALL_SCREEN_ADJ, mMemStates);
+        mStats.computeTotalMemoryUse(totalMem, now);
+
+        mMemInfo = new MemInfo(mContext, totalMem, memTotalTime);
+
+        ProcessDataCollection bgTotals = new ProcessDataCollection(
+                ProcessStats.ALL_SCREEN_ADJ, mMemStates, mStates);
+        ProcessDataCollection runTotals = new ProcessDataCollection(
+                ProcessStats.ALL_SCREEN_ADJ, mMemStates, ProcessStats.NON_CACHED_PROC_STATES);
+
+        createPkgMap(getProcs(bgTotals, runTotals), bgTotals, runTotals);
+
+        ProcStatsPackageEntry osPkg = createOsEntry(bgTotals, runTotals, totalMem,
+                mMemInfo.baseCacheRam);
+        pkgEntries.add(osPkg);
+    }
+
+    private void createPkgMap(ArrayList<ProcStatsEntry> procEntries, ProcessDataCollection bgTotals,
+            ProcessDataCollection runTotals) {
+        // Combine processes into packages.
+        ArrayMap<String, ProcStatsPackageEntry> pkgMap = new ArrayMap<>();
+        for (int i = procEntries.size() - 1; i >= 0; i--) {
+            ProcStatsEntry proc = procEntries.get(i);
+            proc.evaluateTargetPackage(mPm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
+            ProcStatsPackageEntry pkg = pkgMap.get(proc.mBestTargetPackage);
+            if (pkg == null) {
+                pkg = new ProcStatsPackageEntry(proc.mBestTargetPackage, memTotalTime);
+                pkgMap.put(proc.mBestTargetPackage, pkg);
+                pkgEntries.add(pkg);
+            }
+            pkg.addEntry(proc);
+        }
+    }
+
+    private ProcStatsPackageEntry createOsEntry(ProcessDataCollection bgTotals,
+            ProcessDataCollection runTotals, TotalMemoryUseCollection totalMem, long baseCacheRam) {
+        // Add in fake entry representing the OS itself.
+        ProcStatsPackageEntry osPkg = new ProcStatsPackageEntry("os", memTotalTime);
+        ProcStatsEntry osEntry;
+        if (totalMem.sysMemNativeWeight > 0) {
+            osEntry = new ProcStatsEntry("os", 0,
+                    mContext.getString(R.string.process_stats_os_native), memTotalTime,
+                    (long) (totalMem.sysMemNativeWeight / memTotalTime));
+            osEntry.evaluateTargetPackage(mPm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
+            osPkg.addEntry(osEntry);
+        }
+        if (totalMem.sysMemKernelWeight > 0) {
+            osEntry = new ProcStatsEntry("os", 0,
+                    mContext.getString(R.string.process_stats_os_kernel), memTotalTime,
+                    (long) (totalMem.sysMemKernelWeight / memTotalTime));
+            osEntry.evaluateTargetPackage(mPm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
+            osPkg.addEntry(osEntry);
+        }
+        if (totalMem.sysMemZRamWeight > 0) {
+            osEntry = new ProcStatsEntry("os", 0,
+                    mContext.getString(R.string.process_stats_os_zram), memTotalTime,
+                    (long) (totalMem.sysMemZRamWeight / memTotalTime));
+            osEntry.evaluateTargetPackage(mPm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
+            osPkg.addEntry(osEntry);
+        }
+        if (baseCacheRam > 0) {
+            osEntry = new ProcStatsEntry("os", 0,
+                    mContext.getString(R.string.process_stats_os_cache), memTotalTime,
+                    baseCacheRam / 1024);
+            osEntry.evaluateTargetPackage(mPm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
+            osPkg.addEntry(osEntry);
+        }
+        return osPkg;
+    }
+
+    private ArrayList<ProcStatsEntry> getProcs(ProcessDataCollection bgTotals,
+            ProcessDataCollection runTotals) {
+        final ArrayList<ProcStatsEntry> procEntries = new ArrayList<>();
+        if (DEBUG) Log.d(TAG, "-------------------- PULLING PROCESSES");
+
+        final ProcessMap<ProcStatsEntry> entriesMap = new ProcessMap<ProcStatsEntry>();
+        for (int ipkg = 0, N = mStats.mPackages.getMap().size(); ipkg < N; ipkg++) {
+            final SparseArray<SparseArray<ProcessStats.PackageState>> pkgUids = mStats.mPackages
+                    .getMap().valueAt(ipkg);
+            for (int iu = 0; iu < pkgUids.size(); iu++) {
+                final SparseArray<ProcessStats.PackageState> vpkgs = pkgUids.valueAt(iu);
+                for (int iv = 0; iv < vpkgs.size(); iv++) {
+                    final ProcessStats.PackageState st = vpkgs.valueAt(iv);
+                    for (int iproc = 0; iproc < st.mProcesses.size(); iproc++) {
+                        final ProcessStats.ProcessState pkgProc = st.mProcesses.valueAt(iproc);
+                        final ProcessStats.ProcessState proc = mStats.mProcesses.get(pkgProc.mName,
+                                pkgProc.mUid);
+                        if (proc == null) {
+                            Log.w(TAG, "No process found for pkg " + st.mPackageName
+                                    + "/" + st.mUid + " proc name " + pkgProc.mName);
+                            continue;
+                        }
+                        ProcStatsEntry ent = entriesMap.get(proc.mName, proc.mUid);
+                        if (ent == null) {
+                            ent = new ProcStatsEntry(proc, st.mPackageName, bgTotals, runTotals,
+                                    mUseUss);
+                            if (ent.mRunWeight > 0) {
+                                if (DEBUG) Log.d(TAG, "Adding proc " + proc.mName + "/"
+                                            + proc.mUid + ": time="
+                                            + ProcessStatsUi.makeDuration(ent.mRunDuration) + " ("
+                                            + ((((double) ent.mRunDuration) / memTotalTime) * 100)
+                                            + "%)"
+                                            + " pss=" + ent.mAvgRunMem);
+                                entriesMap.put(proc.mName, proc.mUid, ent);
+                                procEntries.add(ent);
+                            }
+                        } else {
+                            ent.addPackage(st.mPackageName);
+                        }
+                    }
+                }
+            }
+        }
+
+        if (DEBUG) Log.d(TAG, "-------------------- MAPPING SERVICES");
+
+        // Add in service info.
+        for (int ip = 0, N = mStats.mPackages.getMap().size(); ip < N; ip++) {
+            SparseArray<SparseArray<ProcessStats.PackageState>> uids = mStats.mPackages.getMap()
+                    .valueAt(ip);
+            for (int iu = 0; iu < uids.size(); iu++) {
+                SparseArray<ProcessStats.PackageState> vpkgs = uids.valueAt(iu);
+                for (int iv = 0; iv < vpkgs.size(); iv++) {
+                    ProcessStats.PackageState ps = vpkgs.valueAt(iv);
+                    for (int is = 0, NS = ps.mServices.size(); is < NS; is++) {
+                        ProcessStats.ServiceState ss = ps.mServices.valueAt(is);
+                        if (ss.mProcessName != null) {
+                            ProcStatsEntry ent = entriesMap.get(ss.mProcessName,
+                                    uids.keyAt(iu));
+                            if (ent != null) {
+                                if (DEBUG) Log.d(TAG, "Adding service " + ps.mPackageName
+                                            + "/" + ss.mName + "/" + uids.keyAt(iu) + " to proc "
+                                            + ss.mProcessName);
+                                ent.addService(ss);
+                            } else {
+                                Log.w(TAG, "No process " + ss.mProcessName + "/" + uids.keyAt(iu)
+                                        + " for service " + ss.mName);
+                            }
+                        }
+                    }
+                }
+            }
+        }
+
+        return procEntries;
+    }
+
+    private void load() {
+        try {
+            mMemState = mProcessStats.getCurrentMemoryState();
+            ParcelFileDescriptor pfd = mProcessStats.getStatsOverTime(mDuration);
+            mStats = new ProcessStats(false);
+            InputStream is = new ParcelFileDescriptor.AutoCloseInputStream(pfd);
+            mStats.read(is);
+            try {
+                is.close();
+            } catch (IOException e) {
+            }
+            if (mStats.mReadError != null) {
+                Log.w(TAG, "Failure reading process stats: " + mStats.mReadError);
+            }
+        } catch (RemoteException e) {
+            Log.e(TAG, "RemoteException:", e);
+        }
+    }
+
+    public static class MemInfo {
+        double realUsedRam;
+        double realFreeRam;
+        double realTotalRam;
+        long baseCacheRam;
+
+        double[] mMemStateWeights = new double[ProcessStats.STATE_COUNT];
+        double freeWeight;
+        double usedWeight;
+        double weightToRam;
+        double totalRam;
+        double totalScale;
+
+        private MemInfo(Context context, ProcessStats.TotalMemoryUseCollection totalMem,
+                long memTotalTime) {
+            calculateWeightInfo(context, totalMem, memTotalTime);
+
+            double usedRam = (usedWeight * 1024) / memTotalTime;
+            double freeRam = (freeWeight * 1024) / memTotalTime;
+            totalRam = usedRam + freeRam;
+            totalScale = realTotalRam / totalRam;
+            weightToRam = totalScale / memTotalTime * 1024;
+
+            realUsedRam = usedRam * totalScale;
+            realFreeRam = freeRam * totalScale;
+            if (DEBUG) {
+                Log.i(TAG, "Scaled Used RAM: " + Formatter.formatShortFileSize(context,
+                        (long) realUsedRam));
+                Log.i(TAG, "Scaled Free RAM: " + Formatter.formatShortFileSize(context,
+                        (long) realFreeRam));
+            }
+            if (DEBUG) {
+                Log.i(TAG, "Adj Scaled Used RAM: " + Formatter.formatShortFileSize(context,
+                        (long) realUsedRam));
+                Log.i(TAG, "Adj Scaled Free RAM: " + Formatter.formatShortFileSize(context,
+                        (long) realFreeRam));
+            }
+
+            ActivityManager.MemoryInfo memInfo = new ActivityManager.MemoryInfo();
+            ((ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE)).getMemoryInfo(
+                    memInfo);
+            if (memInfo.hiddenAppThreshold >= realFreeRam) {
+                realUsedRam = freeRam;
+                realFreeRam = 0;
+                baseCacheRam = (long) realFreeRam;
+            } else {
+                realUsedRam += memInfo.hiddenAppThreshold;
+                realFreeRam -= memInfo.hiddenAppThreshold;
+                baseCacheRam = memInfo.hiddenAppThreshold;
+            }
+        }
+
+        private void calculateWeightInfo(Context context, TotalMemoryUseCollection totalMem,
+                long memTotalTime) {
+            MemInfoReader memReader = new MemInfoReader();
+            memReader.readMemInfo();
+            realTotalRam = memReader.getTotalSize();
+            freeWeight = totalMem.sysMemFreeWeight + totalMem.sysMemCachedWeight;
+            usedWeight = totalMem.sysMemKernelWeight + totalMem.sysMemNativeWeight
+                    + totalMem.sysMemZRamWeight;
+            for (int i = 0; i < ProcessStats.STATE_COUNT; i++) {
+                if (i == ProcessStats.STATE_SERVICE_RESTARTING) {
+                    // These don't really run.
+                    mMemStateWeights[i] = 0;
+                } else {
+                    mMemStateWeights[i] = totalMem.processStateWeight[i];
+                    if (i >= ProcessStats.STATE_HOME) {
+                        freeWeight += totalMem.processStateWeight[i];
+                    } else {
+                        usedWeight += totalMem.processStateWeight[i];
+                    }
+                }
+            }
+            if (DEBUG) {
+                Log.i(TAG, "Used RAM: " + Formatter.formatShortFileSize(context,
+                        (long) ((usedWeight * 1024) / memTotalTime)));
+                Log.i(TAG, "Free RAM: " + Formatter.formatShortFileSize(context,
+                        (long) ((freeWeight * 1024) / memTotalTime)));
+                Log.i(TAG, "Total RAM: " + Formatter.formatShortFileSize(context,
+                        (long) (((freeWeight + usedWeight) * 1024) / memTotalTime)));
+            }
+        }
+    }
+
+    final static Comparator<ProcStatsEntry> sEntryCompare = new Comparator<ProcStatsEntry>() {
+        @Override
+        public int compare(ProcStatsEntry lhs, ProcStatsEntry rhs) {
+            if (lhs.mRunWeight < rhs.mRunWeight) {
+                return 1;
+            } else if (lhs.mRunWeight > rhs.mRunWeight) {
+                return -1;
+            } else if (lhs.mRunDuration < rhs.mRunDuration) {
+                return 1;
+            } else if (lhs.mRunDuration > rhs.mRunDuration) {
+                return -1;
+            }
+            return 0;
+        }
+    };
+}
diff --git a/src/com/android/settings/applications/ProcStatsEntry.java b/src/com/android/settings/applications/ProcStatsEntry.java
index 41f7a53..637003c 100644
--- a/src/com/android/settings/applications/ProcStatsEntry.java
+++ b/src/com/android/settings/applications/ProcStatsEntry.java
@@ -36,6 +36,7 @@
     final String mPackage;
     final int mUid;
     final String mName;
+    public CharSequence mLabel;
     final ArrayList<String> mPackages = new ArrayList<String>();
     final long mBgDuration;
     final long mAvgBgMem;
diff --git a/src/com/android/settings/applications/ProcStatsPackageEntry.java b/src/com/android/settings/applications/ProcStatsPackageEntry.java
index 3925d1d..feb11d8 100644
--- a/src/com/android/settings/applications/ProcStatsPackageEntry.java
+++ b/src/com/android/settings/applications/ProcStatsPackageEntry.java
@@ -30,6 +30,9 @@
     private static final String TAG = "ProcStatsEntry";
     private static boolean DEBUG = ProcessStatsUi.DEBUG;
 
+    private static final float ALWAYS_THRESHOLD = .95f;
+    private static final float SOMETIMES_THRESHOLD = .25f;
+
     final String mPackage;
     final ArrayList<ProcStatsEntry> mEntries = new ArrayList<ProcStatsEntry>();
 
@@ -44,9 +47,11 @@
 
     public ApplicationInfo mUiTargetApp;
     public String mUiLabel;
+    private long mWindowLength;
 
-    public ProcStatsPackageEntry(String pkg) {
+    public ProcStatsPackageEntry(String pkg, long windowLength) {
         mPackage = pkg;
+        mWindowLength = windowLength;
     }
 
     public ProcStatsPackageEntry(Parcel in) {
@@ -62,6 +67,16 @@
         mRunWeight = in.readDouble();
     }
 
+    public CharSequence getRunningFrequency(Context context) {
+        float amountRunning = mRunDuration / (float) mWindowLength;
+        return getFrequency(amountRunning, context);
+    }
+
+    public CharSequence getBackgroundFrequency(Context context) {
+        float amountRunning = mBgDuration / (float) mWindowLength;
+        return getFrequency(amountRunning, context);
+    }
+
     public void addEntry(ProcStatsEntry entry) {
         mEntries.add(entry);
     }
@@ -72,23 +87,28 @@
         mRunDuration = mAvgRunMem = mMaxRunMem = 0;
         mRunWeight = 0;
         final int N = mEntries.size();
-        for (int i=0; i<N; i++) {
+        for (int i=0; i < N; i++) {
             ProcStatsEntry entry = mEntries.get(i);
             mBgDuration += entry.mBgDuration;
-            mAvgBgMem += entry.mAvgBgMem;
-            if (entry.mMaxBgMem > mMaxBgMem) {
-                mMaxBgMem = entry.mMaxBgMem;
-            }
+            mAvgBgMem += entry.mAvgBgMem * entry.mBgDuration;
             mBgWeight += entry.mBgWeight;
             mRunDuration += entry.mRunDuration;
-            mAvgRunMem += entry.mAvgRunMem;
-            if (entry.mMaxRunMem > mMaxRunMem) {
-                mMaxRunMem = entry.mMaxRunMem;
-            }
+            mAvgRunMem += entry.mAvgRunMem * entry.mRunDuration;
             mRunWeight += entry.mRunWeight;
+
+            // Each entry is generally a process or something similar.  Since it is extremely
+            // unlikely that any apps are going to avoid running processes at the same time
+            // to avoid memory usage, we will sum the maximum memory usage to create a
+            // hypothetical worst case scenario of memory.
+            mMaxBgMem += entry.mMaxBgMem;
+            mMaxRunMem += entry.mMaxRunMem;
         }
-        mAvgBgMem /= N;
-        mAvgRunMem /= N;
+        if (mBgDuration != 0) {
+            mAvgBgMem = mAvgBgMem * N / mBgDuration;
+        }
+        if (mRunDuration != 0) {
+            mAvgRunMem = mAvgRunMem * N / mRunDuration;
+        }
     }
 
     public void retrieveUiData(Context context, PackageManager pm) {
@@ -142,4 +162,15 @@
             return new ProcStatsPackageEntry[size];
         }
     };
+
+    // TODO: Find better place for this.
+    public static CharSequence getFrequency(float amount, Context context) {
+        if (amount> ALWAYS_THRESHOLD) {
+            return context.getString(R.string.always_running);
+        } else if (amount> SOMETIMES_THRESHOLD) {
+            return context.getString(R.string.sometimes_running);
+        } else {
+            return context.getString(R.string.rarely_running);
+        }
+    }
 }
diff --git a/src/com/android/settings/applications/ProcessStatsDetail.java b/src/com/android/settings/applications/ProcessStatsDetail.java
index 1e7cf09..191e7e9 100644
--- a/src/com/android/settings/applications/ProcessStatsDetail.java
+++ b/src/com/android/settings/applications/ProcessStatsDetail.java
@@ -17,60 +17,77 @@
 package com.android.settings.applications;
 
 import android.app.ActivityManager;
+import android.app.ActivityManager.RunningServiceInfo;
+import android.app.AlertDialog;
 import android.app.admin.DevicePolicyManager;
+import android.content.ComponentName;
 import android.content.Context;
+import android.content.DialogInterface;
+import android.content.Intent;
 import android.content.pm.ApplicationInfo;
 import android.content.pm.PackageManager;
+import android.content.pm.PackageManager.NameNotFoundException;
+import android.content.pm.ServiceInfo;
+import android.graphics.drawable.ColorDrawable;
 import android.os.Bundle;
 import android.os.Process;
+import android.preference.PreferenceCategory;
 import android.text.format.Formatter;
-import android.view.LayoutInflater;
+import android.util.ArrayMap;
+import android.util.Log;
 import android.view.View;
-import android.view.ViewGroup;
 import android.widget.Button;
-import android.widget.ImageView;
-import android.widget.ProgressBar;
 import android.widget.TextView;
+
 import com.android.internal.logging.MetricsLogger;
-import com.android.settings.InstrumentedFragment;
+import com.android.settings.AppHeader;
+import com.android.settings.CancellablePreference;
+import com.android.settings.CancellablePreference.OnCancelListener;
 import com.android.settings.R;
-import com.android.settings.Utils;
+import com.android.settings.SettingsPreferenceFragment;
+import com.android.settings.applications.ProcStatsEntry.Service;
 
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.Comparator;
 import java.util.HashMap;
+import java.util.List;
 
-import static com.android.settings.Utils.prepareCustomPreferencesList;
+public class ProcessStatsDetail extends SettingsPreferenceFragment
+        implements Button.OnClickListener {
 
-public class ProcessStatsDetail extends InstrumentedFragment implements Button.OnClickListener {
     private static final String TAG = "ProcessStatsDetail";
 
     public static final int ACTION_FORCE_STOP = 1;
 
     public static final String EXTRA_PACKAGE_ENTRY = "package_entry";
     public static final String EXTRA_USE_USS = "use_uss";
-    public static final String EXTRA_MAX_WEIGHT = "max_weight";
     public static final String EXTRA_WEIGHT_TO_RAM = "weight_to_ram";
     public static final String EXTRA_TOTAL_TIME = "total_time";
+    public static final String EXTRA_MAX_MEMORY_USAGE = "max_memory_usage";
+    public static final String EXTRA_TOTAL_SCALE = "total_scale";
+
+    private static final String KEY_DETAILS_HEADER = "details_header";
+
+    private final ArrayMap<ComponentName, CancellablePreference> mServiceMap = new ArrayMap<>();
 
     private PackageManager mPm;
     private DevicePolicyManager mDpm;
 
     private ProcStatsPackageEntry mApp;
     private boolean mUseUss;
-    private double mMaxWeight;
     private double mWeightToRam;
     private long mTotalTime;
     private long mOnePercentTime;
 
-    private View mRootView;
-    private TextView mTitleView;
-    private ViewGroup mTwoButtonsPanel;
     private Button mForceStopButton;
     private Button mReportButton;
-    private ViewGroup mProcessesParent;
-    private ViewGroup mServicesParent;
+
+    private LinearColorBar mColorBar;
+
+    private float mMaxMemoryUsage;
+
+    private double mTotalScale;
 
     @Override
     public void onCreate(Bundle icicle) {
@@ -81,21 +98,23 @@
         mApp = args.getParcelable(EXTRA_PACKAGE_ENTRY);
         mApp.retrieveUiData(getActivity(), mPm);
         mUseUss = args.getBoolean(EXTRA_USE_USS);
-        mMaxWeight = args.getDouble(EXTRA_MAX_WEIGHT);
         mWeightToRam = args.getDouble(EXTRA_WEIGHT_TO_RAM);
         mTotalTime = args.getLong(EXTRA_TOTAL_TIME);
+        mMaxMemoryUsage = args.getFloat(EXTRA_MAX_MEMORY_USAGE);
+        mTotalScale = args.getDouble(EXTRA_TOTAL_SCALE);
         mOnePercentTime = mTotalTime/100;
+
+        mServiceMap.clear();
+        createDetails();
     }
 
     @Override
-    public View onCreateView(
-            LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
-        final View view = inflater.inflate(R.layout.process_stats_details, container, false);
-        prepareCustomPreferencesList(container, view, view, false);
+    public void onViewCreated(View view, Bundle savedInstanceState) {
+        super.onViewCreated(view, savedInstanceState);
 
-        mRootView = view;
-        createDetails();
-        return view;
+        AppHeader.createAppHeader(getActivity(),
+                mApp.mUiTargetApp != null ? mApp.mUiTargetApp.loadIcon(mPm) : new ColorDrawable(0),
+                mApp.mUiLabel, null);
     }
 
     @Override
@@ -107,56 +126,88 @@
     public void onResume() {
         super.onResume();
         checkForceStop();
+
+        updateRunningServices();
     }
 
-    @Override
-    public void onPause() {
-        super.onPause();
+    private void updateRunningServices() {
+        ActivityManager activityManager = (ActivityManager)
+                getActivity().getSystemService(Context.ACTIVITY_SERVICE);
+        List<RunningServiceInfo> runningServices =
+                activityManager.getRunningServices(Integer.MAX_VALUE);
+
+        // Set all services as not running, then turn back on the ones we find.
+        int N = mServiceMap.size();
+        for (int i = 0; i < N; i++) {
+            mServiceMap.valueAt(i).setCancellable(false);
+        }
+
+        N = runningServices.size();
+        for (int i = 0; i < N; i++) {
+            RunningServiceInfo runningService = runningServices.get(i);
+            if (!runningService.started && runningService.clientLabel == 0) {
+                continue;
+            }
+            if ((runningService.flags & RunningServiceInfo.FLAG_PERSISTENT_PROCESS) != 0) {
+                continue;
+            }
+            final ComponentName service = runningService.service;
+            CancellablePreference pref = mServiceMap.get(service);
+            if (pref != null) {
+                pref.setOnCancelListener(new OnCancelListener() {
+                    @Override
+                    public void onCancel(CancellablePreference preference) {
+                        stopService(service.getPackageName(), service.getClassName());
+                    }
+                });
+                pref.setCancellable(true);
+            }
+        }
     }
 
     private void createDetails() {
-        final double percentOfWeight = (mApp.mBgWeight / mMaxWeight) * 100;
-
-        int appLevel = (int) Math.ceil(percentOfWeight);
-        String appLevelText = Formatter.formatShortFileSize(getActivity(),
-                (long)(mApp.mRunWeight * mWeightToRam));
-
-        // Set all values in the header.
-        mTitleView = (TextView) mRootView.findViewById(android.R.id.title);
-        mTitleView.setText(mApp.mUiLabel);
-        final TextView text1 = (TextView)mRootView.findViewById(android.R.id.text1);
-        text1.setText(appLevelText);
-        final ProgressBar progress = (ProgressBar) mRootView.findViewById(android.R.id.progress);
-        progress.setProgress(appLevel);
-        final ImageView icon = (ImageView) mRootView.findViewById(android.R.id.icon);
-        if (mApp.mUiTargetApp != null) {
-            icon.setImageDrawable(mApp.mUiTargetApp.loadIcon(mPm));
-        }
-
-        mTwoButtonsPanel = (ViewGroup)mRootView.findViewById(R.id.two_buttons_panel);
-        mForceStopButton = (Button)mRootView.findViewById(R.id.right_button);
-        mReportButton = (Button)mRootView.findViewById(R.id.left_button);
-        mForceStopButton.setEnabled(false);
-        mReportButton.setVisibility(View.INVISIBLE);
-
-        mProcessesParent = (ViewGroup)mRootView.findViewById(R.id.processes);
-        mServicesParent = (ViewGroup)mRootView.findViewById(R.id.services);
+        addPreferencesFromResource(R.xml.app_memory_settings);
 
         fillProcessesSection();
-        fillServicesSection();
-        if (mServicesParent.getChildCount() <= 0) {
-            mServicesParent.setVisibility(View.GONE);
-            mRootView.findViewById(R.id.services_label).setVisibility(View.GONE);
-        }
+
+        LayoutPreference headerLayout = (LayoutPreference) findPreference(KEY_DETAILS_HEADER);
+
+        TextView avgUsed = (TextView) headerLayout.findViewById(R.id.memory_avg);
+        TextView maxUsed = (TextView) headerLayout.findViewById(R.id.memory_max);
+        avgUsed.setText(getString(R.string.memory_avg_desc,
+                Formatter.formatShortFileSize(getActivity(),
+                        (long) (Math.max(mApp.mBgWeight, mApp.mRunWeight) * mWeightToRam))));
+        maxUsed.setText(getString(R.string.memory_max_desc,
+                Formatter.formatShortFileSize(getActivity(),
+                        (long) (Math.max(mApp.mMaxBgMem, mApp.mMaxRunMem) * 1024 * mTotalScale))));
+
+        mForceStopButton = (Button) headerLayout.findViewById(R.id.right_button);
+        mReportButton = (Button) headerLayout.findViewById(R.id.left_button);
 
         if (mApp.mEntries.get(0).mUid >= android.os.Process.FIRST_APPLICATION_UID) {
+            mForceStopButton.setEnabled(false);
+            mReportButton.setVisibility(View.INVISIBLE);
+
             mForceStopButton.setText(R.string.force_stop);
             mForceStopButton.setTag(ACTION_FORCE_STOP);
             mForceStopButton.setOnClickListener(this);
-            mTwoButtonsPanel.setVisibility(View.VISIBLE);
         } else {
-            mTwoButtonsPanel.setVisibility(View.GONE);
+            mReportButton.setVisibility(View.GONE);
+            mForceStopButton.setVisibility(View.GONE);
         }
+
+        // TODO: Find way to share this code with ProcessStatsPreference.
+        boolean statsForeground = mApp.mRunWeight > mApp.mBgWeight;
+        float mAvgRatio = (statsForeground ? mApp.mAvgRunMem : mApp.mAvgBgMem) / mMaxMemoryUsage;
+        float mMaxRatio = (statsForeground ? mApp.mMaxRunMem : mApp.mMaxBgMem) / mMaxMemoryUsage
+                - mAvgRatio;
+        float mRemainingRatio = 1 - mAvgRatio - mMaxRatio;
+        mColorBar = (LinearColorBar) headerLayout.findViewById(R.id.color_bar);
+        Context context = getActivity();
+        mColorBar.setColors(context.getColor(R.color.memory_avg_use),
+                context.getColor(R.color.memory_max_use),
+                context.getColor(R.color.memory_remaining));
+        mColorBar.setRatios(mAvgRatio, mMaxRatio, mRemainingRatio);
     }
 
     public void onClick(View v) {
@@ -171,34 +222,6 @@
         }
     }
 
-    private void addPackageHeaderItem(ViewGroup parent, String packageName) {
-        LayoutInflater inflater = getActivity().getLayoutInflater();
-        ViewGroup item = (ViewGroup) inflater.inflate(R.layout.running_processes_item,
-                null);
-        parent.addView(item);
-        final ImageView icon = (ImageView) item.findViewById(R.id.icon);
-        TextView nameView = (TextView) item.findViewById(R.id.name);
-        TextView descriptionView = (TextView) item.findViewById(R.id.description);
-        try {
-            ApplicationInfo ai = mPm.getApplicationInfo(packageName, 0);
-            icon.setImageDrawable(ai.loadIcon(mPm));
-            nameView.setText(ai.loadLabel(mPm));
-        } catch (PackageManager.NameNotFoundException e) {
-        }
-        descriptionView.setText(packageName);
-    }
-
-    private void addDetailsItem(ViewGroup parent, CharSequence label, CharSequence value) {
-        LayoutInflater inflater = getActivity().getLayoutInflater();
-        ViewGroup item = (ViewGroup) inflater.inflate(R.layout.power_usage_detail_item_text,
-                null);
-        parent.addView(item);
-        TextView labelView = (TextView) item.findViewById(R.id.label);
-        TextView valueView = (TextView) item.findViewById(R.id.value);
-        labelView.setText(label);
-        valueView.setText(value);
-    }
-
     final static Comparator<ProcStatsEntry> sEntryCompare = new Comparator<ProcStatsEntry>() {
         @Override
         public int compare(ProcStatsEntry lhs, ProcStatsEntry rhs) {
@@ -213,28 +236,35 @@
 
     private void fillProcessesSection() {
         final ArrayList<ProcStatsEntry> entries = new ArrayList<>();
-        for (int ie=0; ie<mApp.mEntries.size(); ie++) {
+        for (int ie = 0; ie < mApp.mEntries.size(); ie++) {
             ProcStatsEntry entry = mApp.mEntries.get(ie);
+            if (entry.mPackage.equals("os")) {
+                entry.mLabel = entry.mName;
+            } else {
+                if (mApp.mEntries.size() > 1) {
+                    entry.mLabel = getString(R.string.process_format, (ie + 1));
+                } else {
+                    entry.mLabel = getString(R.string.process);
+                }
+            }
             entries.add(entry);
         }
         Collections.sort(entries, sEntryCompare);
-        for (int ie=0; ie<entries.size(); ie++) {
+        for (int ie = 0; ie < entries.size(); ie++) {
             ProcStatsEntry entry = entries.get(ie);
-            LayoutInflater inflater = getActivity().getLayoutInflater();
-            ViewGroup item = (ViewGroup) inflater.inflate(R.layout.process_stats_proc_details,
-                    null);
-            mProcessesParent.addView(item);
-            ((TextView)item.findViewById(R.id.processes_name)).setText(entry.mName);
-            addDetailsItem(item, getResources().getText(R.string.process_stats_ram_use),
-                    Formatter.formatShortFileSize(getActivity(),
-                            (long)(entry.mRunWeight * mWeightToRam)));
-            if (entry.mBgWeight > 0) {
-                addDetailsItem(item, getResources().getText(R.string.process_stats_bg_ram_use),
-                        Formatter.formatShortFileSize(getActivity(),
-                                (long)(entry.mBgWeight * mWeightToRam)));
-            }
-            addDetailsItem(item, getResources().getText(R.string.process_stats_run_time),
-                    Utils.formatPercentage(entry.mRunDuration, mTotalTime));
+            PreferenceCategory processPref = new PreferenceCategory(getActivity());
+            processPref.setLayoutResource(R.layout.process_preference_category);
+            processPref.setTitle(entry.mLabel);
+
+            long memoryUse = Math.max((long)(entry.mRunWeight * mWeightToRam),
+                    (long)(entry.mBgWeight * mWeightToRam));
+            String memoryString = Formatter.formatShortFileSize(getActivity(), memoryUse);
+            CharSequence frequency = ProcStatsPackageEntry.getFrequency(entry.mRunDuration
+                    / (float)mTotalTime, getActivity());
+            processPref.setSummary(
+                    getString(R.string.memory_use_running_format, memoryString, frequency));
+            getPreferenceScreen().addPreference(processPref);
+            fillServicesSection(entry, processPref);
         }
     }
 
@@ -268,52 +298,97 @@
         long mDuration;
     }
 
-    private void fillServicesSection() {
+    private void fillServicesSection(ProcStatsEntry entry, PreferenceCategory processPref) {
         final HashMap<String, PkgService> pkgServices = new HashMap<>();
         final ArrayList<PkgService> pkgList = new ArrayList<>();
-        for (int ie=0; ie< mApp.mEntries.size(); ie++) {
-            ProcStatsEntry ent = mApp.mEntries.get(ie);
-            for (int ip=0; ip<ent.mServices.size(); ip++) {
-                String pkg = ent.mServices.keyAt(ip);
-                PkgService psvc = null;
-                ArrayList<ProcStatsEntry.Service> services = ent.mServices.valueAt(ip);
-                for (int is=services.size()-1; is>=0; is--) {
-                    ProcStatsEntry.Service pent = services.get(is);
-                    if (pent.mDuration >= mOnePercentTime) {
+        for (int ip = 0; ip < entry.mServices.size(); ip++) {
+            String pkg = entry.mServices.keyAt(ip);
+            PkgService psvc = null;
+            ArrayList<ProcStatsEntry.Service> services = entry.mServices.valueAt(ip);
+            for (int is=services.size()-1; is>=0; is--) {
+                ProcStatsEntry.Service pent = services.get(is);
+                if (pent.mDuration >= mOnePercentTime) {
+                    if (psvc == null) {
+                        psvc = pkgServices.get(pkg);
                         if (psvc == null) {
-                            psvc = pkgServices.get(pkg);
-                            if (psvc == null) {
-                                psvc = new PkgService();
-                                pkgServices.put(pkg, psvc);
-                                pkgList.add(psvc);
-                            }
+                            psvc = new PkgService();
+                            pkgServices.put(pkg, psvc);
+                            pkgList.add(psvc);
                         }
-                        psvc.mServices.add(pent);
-                        psvc.mDuration += pent.mDuration;
                     }
+                    psvc.mServices.add(pent);
+                    psvc.mDuration += pent.mDuration;
                 }
             }
         }
         Collections.sort(pkgList, sServicePkgCompare);
-        for (int ip=0; ip<pkgList.size(); ip++) {
+        for (int ip = 0; ip < pkgList.size(); ip++) {
             ArrayList<ProcStatsEntry.Service> services = pkgList.get(ip).mServices;
             Collections.sort(services, sServiceCompare);
-            if (pkgList.size() > 1) {
-                addPackageHeaderItem(mServicesParent, services.get(0).mPackage);
-            }
             for (int is=0; is<services.size(); is++) {
-                ProcStatsEntry.Service service = services.get(is);
-                String label = service.mName;
-                int tail = label.lastIndexOf('.');
-                if (tail >= 0 && tail < (label.length()-1)) {
-                    label = label.substring(tail+1);
-                }
-                String percentage = Utils.formatPercentage(service.mDuration, mTotalTime);
-                addDetailsItem(mServicesParent, label, percentage);
+                final ProcStatsEntry.Service service = services.get(is);
+                CharSequence label = getLabel(service);
+                CancellablePreference servicePref = new CancellablePreference(getActivity());
+                servicePref.setSelectable(false);
+                servicePref.setTitle(label);
+                servicePref.setSummary(ProcStatsPackageEntry.getFrequency(
+                        service.mDuration / (float) mTotalTime, getActivity()));
+                processPref.addPreference(servicePref);
+                mServiceMap.put(new ComponentName(service.mPackage, service.mName), servicePref);
             }
         }
     }
 
+    private CharSequence getLabel(Service service) {
+        // Try to get the service label, on the off chance that one exists.
+        try {
+            ServiceInfo serviceInfo = getPackageManager().getServiceInfo(
+                    new ComponentName(service.mPackage, service.mName), 0);
+            if (serviceInfo.labelRes != 0) {
+                return serviceInfo.loadLabel(getPackageManager());
+            }
+        } catch (NameNotFoundException e) {
+        }
+        String label = service.mName;
+        int tail = label.lastIndexOf('.');
+        if (tail >= 0 && tail < (label.length()-1)) {
+            label = label.substring(tail+1);
+        }
+        return label;
+    }
+
+    private void stopService(String pkg, String name) {
+        try {
+            ApplicationInfo appInfo = getActivity().getPackageManager().getApplicationInfo(pkg, 0);
+            if ((appInfo.flags & ApplicationInfo.FLAG_SYSTEM) != 0) {
+                showStopServiceDialog(pkg, name);
+                return;
+            }
+        } catch (NameNotFoundException e) {
+            Log.e(TAG, "Can't find app " + pkg, e);
+            return;
+        }
+        doStopService(pkg, name);
+    }
+
+    private void showStopServiceDialog(final String pkg, final String name) {
+        new AlertDialog.Builder(getActivity())
+                .setTitle(R.string.runningservicedetails_stop_dlg_title)
+                .setMessage(R.string.runningservicedetails_stop_dlg_text)
+                .setPositiveButton(R.string.dlg_ok, new DialogInterface.OnClickListener() {
+                    public void onClick(DialogInterface dialog, int which) {
+                        doStopService(pkg, name);
+                    }
+                })
+                .setNegativeButton(R.string.dlg_cancel, null)
+                .show();
+    }
+
+    private void doStopService(String pkg, String name) {
+        getActivity().stopService(new Intent().setClassName(pkg, name));
+        updateRunningServices();
+    }
+
     private void killProcesses() {
         ActivityManager am = (ActivityManager)getActivity().getSystemService(
                 Context.ACTIVITY_SERVICE);
diff --git a/src/com/android/settings/applications/ProcessStatsPreference.java b/src/com/android/settings/applications/ProcessStatsPreference.java
index 182cf0e..a1725e3 100644
--- a/src/com/android/settings/applications/ProcessStatsPreference.java
+++ b/src/com/android/settings/applications/ProcessStatsPreference.java
@@ -17,20 +17,25 @@
 package com.android.settings.applications;
 
 import android.content.Context;
+import android.content.pm.PackageManager;
 import android.graphics.drawable.ColorDrawable;
-import android.graphics.drawable.Drawable;
 import android.preference.Preference;
-import android.text.format.Formatter;
+import android.text.TextUtils;
 import android.util.AttributeSet;
+import android.util.Log;
 import android.view.View;
-import android.widget.ProgressBar;
-import android.widget.TextView;
+
 import com.android.settings.R;
 
 public class ProcessStatsPreference extends Preference {
+
     private ProcStatsPackageEntry mEntry;
-    private int mProgress;
-    private CharSequence mProgressText;
+    private final int mAvgColor;
+    private final int mMaxColor;
+    private final int mRemainingColor;
+    private float mAvgRatio;
+    private float mMaxRatio;
+    private float mRemainingRatio;
 
     public ProcessStatsPreference(Context context) {
         this(context, null);
@@ -47,33 +52,38 @@
     public ProcessStatsPreference(Context context, AttributeSet attrs, int defStyleAttr,
             int defStyleRes) {
         super(context, attrs, defStyleAttr, defStyleRes);
-        setLayoutResource(R.layout.preference_app_percentage);
+        setLayoutResource(R.layout.app_item_linear_color);
+        mAvgColor = context.getColor(R.color.memory_avg_use);
+        mMaxColor = context.getColor(R.color.memory_max_use);
+        mRemainingColor = context.getColor(R.color.memory_remaining);
     }
 
-    public void init(Drawable icon, ProcStatsPackageEntry entry) {
+    public void init(ProcStatsPackageEntry entry, PackageManager pm, float maxMemory) {
         mEntry = entry;
-        setIcon(icon != null ? icon : new ColorDrawable(0));
+        setTitle(TextUtils.isEmpty(entry.mUiLabel) ? entry.mPackage : entry.mUiLabel);
+        if (entry.mUiTargetApp != null) {
+            setIcon(entry.mUiTargetApp.loadIcon(pm));
+        } else {
+            setIcon(new ColorDrawable(0));
+        }
+        boolean statsForeground = entry.mRunWeight > entry.mBgWeight;
+        setSummary(statsForeground ? entry.getRunningFrequency(getContext())
+                : entry.getBackgroundFrequency(getContext()));
+        mAvgRatio = (statsForeground ? entry.mAvgRunMem : entry.mAvgBgMem) / maxMemory;
+        mMaxRatio = (statsForeground ? entry.mMaxRunMem : entry.mMaxBgMem) / maxMemory - mAvgRatio;
+        mRemainingRatio = 1 - mAvgRatio - mMaxRatio;
     }
 
     public ProcStatsPackageEntry getEntry() {
         return mEntry;
     }
 
-    public void setPercent(double percentOfWeight, double percentOfTime, long memory) {
-        mProgress = (int) Math.ceil(percentOfWeight);
-        //mProgressText = Utils.formatPercentage((int) percentOfTime);
-        mProgressText = Formatter.formatShortFileSize(getContext(), memory);
-        notifyChanged();
-    }
-
     @Override
     protected void onBindView(View view) {
         super.onBindView(view);
 
-        final ProgressBar progress = (ProgressBar) view.findViewById(android.R.id.progress);
-        progress.setProgress(mProgress);
-
-        final TextView text1 = (TextView) view.findViewById(android.R.id.text1);
-        text1.setText(mProgressText);
+        LinearColorBar linearColorBar = (LinearColorBar) view.findViewById(R.id.linear_color_bar);
+        linearColorBar.setColors(mAvgColor, mMaxColor, mRemainingColor);
+        linearColorBar.setRatios(mAvgRatio, mMaxRatio, mRemainingRatio);
     }
 }
diff --git a/src/com/android/settings/applications/ProcessStatsUi.java b/src/com/android/settings/applications/ProcessStatsUi.java
index 45e24dd..96f76c0 100644
--- a/src/com/android/settings/applications/ProcessStatsUi.java
+++ b/src/com/android/settings/applications/ProcessStatsUi.java
@@ -16,82 +16,59 @@
 
 package com.android.settings.applications;
 
-import android.app.ActivityManager;
 import android.content.Context;
 import android.content.pm.PackageManager;
-import android.content.res.Resources;
 import android.os.Bundle;
-import android.os.ParcelFileDescriptor;
-import android.os.RemoteException;
-import android.os.ServiceManager;
-import android.os.SystemClock;
-import android.os.UserManager;
 import android.preference.Preference;
-import android.preference.PreferenceFragment;
 import android.preference.PreferenceGroup;
 import android.preference.PreferenceScreen;
 import android.text.format.Formatter;
 import android.util.Log;
-import android.util.SparseArray;
 import android.util.TimeUtils;
 import android.view.Menu;
 import android.view.MenuInflater;
 import android.view.MenuItem;
 import android.view.SubMenu;
-import com.android.internal.app.IProcessStats;
-import com.android.internal.app.ProcessMap;
+import android.widget.TextView;
+
 import com.android.internal.app.ProcessStats;
 import com.android.internal.logging.MetricsLogger;
-import com.android.internal.util.MemInfoReader;
 import com.android.settings.InstrumentedPreferenceFragment;
 import com.android.settings.R;
 import com.android.settings.SettingsActivity;
 import com.android.settings.Utils;
+import com.android.settings.applications.ProcStatsData.MemInfo;
 
-import java.io.IOException;
-import java.io.InputStream;
-import java.util.ArrayList;
 import java.util.Collections;
 import java.util.Comparator;
-import java.util.HashMap;
+import java.util.List;
 
-public class ProcessStatsUi extends InstrumentedPreferenceFragment
-        implements LinearColorBar.OnRegionTappedListener {
+public class ProcessStatsUi extends InstrumentedPreferenceFragment {
+    private static final String MEM_REGION = "mem_region";
+    private static final String STATS_TYPE = "stats_type";
+    private static final String USE_USS = "use_uss";
+    private static final String SHOW_SYSTEM = "show_system";
+    private static final String SHOW_PERCENTAGE = "show_percentage";
+    private static final String DURATION = "duration";
     static final String TAG = "ProcessStatsUi";
     static final boolean DEBUG = false;
 
     private static final String KEY_APP_LIST = "app_list";
-    private static final String KEY_MEM_STATUS = "mem_status";
+    private static final String KEY_STATUS_HEADER = "status_header";
 
     private static final int NUM_DURATIONS = 4;
 
     private static final int MENU_STATS_REFRESH = Menu.FIRST;
     private static final int MENU_DURATION = Menu.FIRST + 1;
-    private static final int MENU_SHOW_SYSTEM = MENU_DURATION + NUM_DURATIONS;
+    private static final int MENU_SHOW_PERCENTAGE = MENU_DURATION + NUM_DURATIONS;
+    private static final int MENU_SHOW_SYSTEM = MENU_SHOW_PERCENTAGE + 1;
     private static final int MENU_USE_USS = MENU_SHOW_SYSTEM + 1;
     private static final int MENU_TYPE_BACKGROUND = MENU_USE_USS + 1;
     private static final int MENU_TYPE_FOREGROUND = MENU_TYPE_BACKGROUND + 1;
     private static final int MENU_TYPE_CACHED = MENU_TYPE_FOREGROUND + 1;
-    private static final int MENU_HELP = MENU_TYPE_CACHED + 1;
 
     static final int MAX_ITEMS_TO_LIST = 60;
 
-    final static Comparator<ProcStatsEntry> sEntryCompare = new Comparator<ProcStatsEntry>() {
-        @Override
-        public int compare(ProcStatsEntry lhs, ProcStatsEntry rhs) {
-            if (lhs.mRunWeight < rhs.mRunWeight) {
-                return 1;
-            } else if (lhs.mRunWeight > rhs.mRunWeight) {
-                return -1;
-            } else if (lhs.mRunDuration < rhs.mRunDuration) {
-                return 1;
-            } else if (lhs.mRunDuration > rhs.mRunDuration) {
-                return -1;
-            }
-            return 0;
-        }
-    };
-
     final static Comparator<ProcStatsPackageEntry> sPackageEntryCompare
             = new Comparator<ProcStatsPackageEntry>() {
         @Override
@@ -109,21 +86,13 @@
         }
     };
 
-    private static ProcessStats sStatsXfer;
-
-    IProcessStats mProcessStats;
-    UserManager mUm;
-    ProcessStats mStats;
-    int mMemState;
-
-    private long mDuration;
-    private long mLastDuration;
+    private boolean mShowPercentage;
     private boolean mShowSystem;
     private boolean mUseUss;
-    private int mStatsType;
     private int mMemRegion;
 
     private MenuItem[] mDurationMenus = new MenuItem[NUM_DURATIONS];
+    private MenuItem mShowPercentageMenu;
     private MenuItem mShowSystemMenu;
     private MenuItem mUseUssMenu;
     private MenuItem mTypeBackgroundMenu;
@@ -131,20 +100,18 @@
     private MenuItem mTypeCachedMenu;
 
     private PreferenceGroup mAppListGroup;
-    private Preference mMemStatusPref;
+    private TextView mMemStatus;
 
-    double mMaxWeight;
-    long mTotalTime;
+    private long mTotalTime;
 
-    long[] mMemTimes = new long[ProcessStats.ADJ_MEM_FACTOR_COUNT];
-    double[] mMemStateWeights = new double[ProcessStats.STATE_COUNT];
-    double mMemCachedWeight;
-    double mMemFreeWeight;
-    double mMemZRamWeight;
-    double mMemKernelWeight;
-    double mMemNativeWeight;
-    double mMemTotalWeight;
-    double mWeightToRam;
+    private long[] mMemTimes = new long[ProcessStats.ADJ_MEM_FACTOR_COUNT];
+    private LinearColorBar mColors;
+    private TextView mMemUsed;
+    private LayoutPreference mHeader;
+    private PackageManager mPm;
+    private long memTotalTime;
+
+    private int mStatsType;
 
     // The actual duration value to use for each duration option.  Note these
     // are lower than the actual duration, since our durations are computed in
@@ -161,26 +128,31 @@
             R.string.menu_duration_12h, R.string.menu_duration_1d
     };
 
+    private ProcStatsData mStatsManager;
+    private float mMaxMemoryUsage;
+
     @Override
     public void onCreate(Bundle icicle) {
         super.onCreate(icicle);
 
-        if (icicle != null) {
-            mStats = sStatsXfer;
-        }
+        mStatsManager = new ProcStatsData(getActivity(), icicle != null);
+
+        mPm = getActivity().getPackageManager();
 
         addPreferencesFromResource(R.xml.process_stats_summary);
-        mProcessStats = IProcessStats.Stub.asInterface(
-                ServiceManager.getService(ProcessStats.SERVICE_NAME));
-        mUm = (UserManager)getActivity().getSystemService(Context.USER_SERVICE);
         mAppListGroup = (PreferenceGroup) findPreference(KEY_APP_LIST);
-        mMemStatusPref = mAppListGroup.findPreference(KEY_MEM_STATUS);
-        mDuration = icicle != null ? icicle.getLong("duration", sDurations[0]) : sDurations[0];
-        mShowSystem = icicle != null ? icicle.getBoolean("show_system") : false;
-        mUseUss = icicle != null ? icicle.getBoolean("use_uss") : false;
-        mStatsType = icicle != null ? icicle.getInt("stats_type", MENU_TYPE_BACKGROUND)
+        mHeader = (LayoutPreference)mAppListGroup.findPreference(KEY_STATUS_HEADER);
+        mMemStatus = (TextView) mHeader.findViewById(R.id.memory_state);
+        mColors = (LinearColorBar) mHeader.findViewById(R.id.color_bar);
+        mMemUsed = (TextView) mHeader.findViewById(R.id.memory_used);
+        mStatsManager.setDuration(icicle != null
+                ? icicle.getLong(DURATION, sDurations[0]) : sDurations[0]);
+        mShowPercentage = icicle != null ? icicle.getBoolean(SHOW_PERCENTAGE) : true;
+        mShowSystem = icicle != null ? icicle.getBoolean(SHOW_SYSTEM) : false;
+        mUseUss = icicle != null ? icicle.getBoolean(USE_USS) : false;
+        mStatsType = icicle != null ? icicle.getInt(STATS_TYPE, MENU_TYPE_BACKGROUND)
                 : MENU_TYPE_BACKGROUND;
-        mMemRegion = icicle != null ? icicle.getInt("mem_region", LinearColorBar.REGION_GREEN)
+        mMemRegion = icicle != null ? icicle.getInt(MEM_REGION, LinearColorBar.REGION_GREEN)
                 : LinearColorBar.REGION_GREEN;
         setHasOptionsMenu(true);
     }
@@ -193,47 +165,31 @@
     @Override
     public void onResume() {
         super.onResume();
-        refreshStats();
+        mStatsManager.refreshStats(false);
+        refreshUi();
     }
 
     @Override
     public void onSaveInstanceState(Bundle outState) {
         super.onSaveInstanceState(outState);
-        outState.putLong("duration", mDuration);
-        outState.putBoolean("show_system", mShowSystem);
-        outState.putBoolean("use_uss", mUseUss);
-        outState.putInt("stats_type", mStatsType);
-        outState.putInt("mem_region", mMemRegion);
+        outState.putLong(DURATION, mStatsManager.getDuration());
+        outState.putBoolean(SHOW_PERCENTAGE, mShowPercentage);
+        outState.putBoolean(SHOW_SYSTEM, mShowSystem);
+        outState.putBoolean(USE_USS, mUseUss);
+        outState.putInt(STATS_TYPE, mStatsType);
+        outState.putInt(MEM_REGION, mMemRegion);
     }
 
     @Override
     public void onDestroy() {
         super.onDestroy();
         if (getActivity().isChangingConfigurations()) {
-            sStatsXfer = mStats;
+            mStatsManager.xferStats();
         }
     }
 
     @Override
     public boolean onPreferenceTreeClick(PreferenceScreen preferenceScreen, Preference preference) {
-        if (preference instanceof LinearColorPreference) {
-            Bundle args = new Bundle();
-            args.putLongArray(ProcessStatsMemDetail.EXTRA_MEM_TIMES, mMemTimes);
-            args.putDoubleArray(ProcessStatsMemDetail.EXTRA_MEM_STATE_WEIGHTS, mMemStateWeights);
-            args.putDouble(ProcessStatsMemDetail.EXTRA_MEM_CACHED_WEIGHT, mMemCachedWeight);
-            args.putDouble(ProcessStatsMemDetail.EXTRA_MEM_FREE_WEIGHT, mMemFreeWeight);
-            args.putDouble(ProcessStatsMemDetail.EXTRA_MEM_ZRAM_WEIGHT, mMemZRamWeight);
-            args.putDouble(ProcessStatsMemDetail.EXTRA_MEM_KERNEL_WEIGHT, mMemKernelWeight);
-            args.putDouble(ProcessStatsMemDetail.EXTRA_MEM_NATIVE_WEIGHT, mMemNativeWeight);
-            args.putDouble(ProcessStatsMemDetail.EXTRA_MEM_TOTAL_WEIGHT, mMemTotalWeight);
-            args.putBoolean(ProcessStatsMemDetail.EXTRA_USE_USS, mUseUss);
-            args.putLong(ProcessStatsMemDetail.EXTRA_TOTAL_TIME, mTotalTime);
-            ((SettingsActivity) getActivity()).startPreferencePanel(
-                    ProcessStatsMemDetail.class.getName(), args, R.string.mem_details_title,
-                    null, null, 0);
-            return true;
-        }
-
         if (!(preference instanceof ProcessStatsPreference)) {
             return false;
         }
@@ -242,9 +198,11 @@
         Bundle args = new Bundle();
         args.putParcelable(ProcessStatsDetail.EXTRA_PACKAGE_ENTRY, pgp.getEntry());
         args.putBoolean(ProcessStatsDetail.EXTRA_USE_USS, mUseUss);
-        args.putDouble(ProcessStatsDetail.EXTRA_MAX_WEIGHT, mMaxWeight);
-        args.putDouble(ProcessStatsDetail.EXTRA_WEIGHT_TO_RAM, mWeightToRam);
+        args.putDouble(ProcessStatsDetail.EXTRA_WEIGHT_TO_RAM,
+                mStatsManager.getMemInfo().weightToRam);
         args.putLong(ProcessStatsDetail.EXTRA_TOTAL_TIME, mTotalTime);
+        args.putFloat(ProcessStatsDetail.EXTRA_MAX_MEMORY_USAGE, mMaxMemoryUsage);
+        args.putDouble(ProcessStatsDetail.EXTRA_TOTAL_SCALE, mStatsManager.getMemInfo().totalScale);
         ((SettingsActivity) getActivity()).startPreferencePanel(
                 ProcessStatsDetail.class.getName(), args, R.string.details_title, null, null, 0);
 
@@ -263,41 +221,37 @@
             mDurationMenus[i] = subMenu.add(0, MENU_DURATION+i, 0, sDurationLabels[i])
                             .setCheckable(true);
         }
-        mShowSystemMenu = menu.add(0, MENU_SHOW_SYSTEM, 0, R.string.menu_show_system)
-                .setAlphabeticShortcut('s')
-                .setCheckable(true);
-        mUseUssMenu = menu.add(0, MENU_USE_USS, 0, R.string.menu_use_uss)
-                .setAlphabeticShortcut('u')
-                .setCheckable(true);
-        subMenu = menu.addSubMenu(R.string.menu_proc_stats_type);
-        mTypeBackgroundMenu = subMenu.add(0, MENU_TYPE_BACKGROUND, 0,
-                R.string.menu_proc_stats_type_background)
-                .setAlphabeticShortcut('b')
-                .setCheckable(true);
-        mTypeForegroundMenu = subMenu.add(0, MENU_TYPE_FOREGROUND, 0,
-                R.string.menu_proc_stats_type_foreground)
-                .setAlphabeticShortcut('f')
-                .setCheckable(true);
-        mTypeCachedMenu = subMenu.add(0, MENU_TYPE_CACHED, 0,
-                R.string.menu_proc_stats_type_cached)
-                .setCheckable(true);
+        // Hide these for now, until their need is determined.
+//        mShowPercentageMenu = menu.add(0, MENU_SHOW_PERCENTAGE, 0, R.string.menu_show_percentage)
+//                .setAlphabeticShortcut('p')
+//                .setCheckable(true);
+//        mShowSystemMenu = menu.add(0, MENU_SHOW_SYSTEM, 0, R.string.menu_show_system)
+//                .setAlphabeticShortcut('s')
+//                .setCheckable(true);
+//        mUseUssMenu = menu.add(0, MENU_USE_USS, 0, R.string.menu_use_uss)
+//                .setAlphabeticShortcut('u')
+//                .setCheckable(true);
+//        subMenu = menu.addSubMenu(R.string.menu_proc_stats_type);
+//        mTypeBackgroundMenu = subMenu.add(0, MENU_TYPE_BACKGROUND, 0,
+//                R.string.menu_proc_stats_type_background)
+//                .setAlphabeticShortcut('b')
+//                .setCheckable(true);
+//        mTypeForegroundMenu = subMenu.add(0, MENU_TYPE_FOREGROUND, 0,
+//                R.string.menu_proc_stats_type_foreground)
+//                .setAlphabeticShortcut('f')
+//                .setCheckable(true);
+//        mTypeCachedMenu = subMenu.add(0, MENU_TYPE_CACHED, 0,
+//                R.string.menu_proc_stats_type_cached)
+//                .setCheckable(true);
 
         updateMenus();
-
-        /*
-        String helpUrl;
-        if (!TextUtils.isEmpty(helpUrl = getResources().getString(R.string.help_url_battery))) {
-            final MenuItem help = menu.add(0, MENU_HELP, 0, R.string.help_label);
-            HelpUtils.prepareHelpMenuItem(getActivity(), help, helpUrl);
-        }
-        */
     }
 
     void updateMenus() {
         int closestIndex = 0;
-        long closestDelta = Math.abs(sDurations[0]-mDuration);
-        for (int i=1; i<NUM_DURATIONS; i++) {
-            long delta = Math.abs(sDurations[i]-mDuration);
+        long closestDelta = Math.abs(sDurations[0] - mStatsManager.getDuration());
+        for (int i = 1; i < NUM_DURATIONS; i++) {
+            long delta = Math.abs(sDurations[i] - mStatsManager.getDuration());
             if (delta < closestDelta) {
                 closestDelta = delta;
                 closestIndex = i;
@@ -308,7 +262,10 @@
                 mDurationMenus[i].setChecked(i == closestIndex);
             }
         }
-        mDuration = sDurations[closestIndex];
+        mStatsManager.setDuration(sDurations[closestIndex]);
+        if (mShowPercentageMenu != null) {
+            mShowPercentageMenu.setChecked(mShowPercentage);
+        }
         if (mShowSystemMenu != null) {
             mShowSystemMenu.setChecked(mShowSystem);
             mShowSystemMenu.setEnabled(mStatsType == MENU_TYPE_BACKGROUND);
@@ -332,46 +289,44 @@
         final int id = item.getItemId();
         switch (id) {
             case MENU_STATS_REFRESH:
-                mStats = null;
-                refreshStats();
+                mStatsManager.refreshStats(false);
+                refreshUi();
+                return true;
+            case MENU_SHOW_PERCENTAGE:
+                mShowPercentage = !mShowPercentage;
+                refreshUi();
                 return true;
             case MENU_SHOW_SYSTEM:
                 mShowSystem = !mShowSystem;
-                refreshStats();
+                refreshUi();
                 return true;
             case MENU_USE_USS:
                 mUseUss = !mUseUss;
-                refreshStats();
+                refreshUi();
                 return true;
             case MENU_TYPE_BACKGROUND:
             case MENU_TYPE_FOREGROUND:
             case MENU_TYPE_CACHED:
                 mStatsType = item.getItemId();
-                refreshStats();
+                if (mStatsType == MENU_TYPE_FOREGROUND) {
+                    mStatsManager.setStats(FOREGROUND_PROC_STATES);
+                } else if (mStatsType == MENU_TYPE_CACHED) {
+                    mStatsManager.setStats(CACHED_PROC_STATES);
+                } else {
+                    mStatsManager.setStats(mShowSystem ? BACKGROUND_AND_SYSTEM_PROC_STATES
+                            : ProcessStats.BACKGROUND_PROC_STATES);
+                }
+                refreshUi();
                 return true;
             default:
-                if (id >= MENU_DURATION && id < (MENU_DURATION+NUM_DURATIONS)) {
-                    mDuration = sDurations[id-MENU_DURATION];
-                    refreshStats();
+                if (id >= MENU_DURATION && id < (MENU_DURATION + NUM_DURATIONS)) {
+                    mStatsManager.setDuration(sDurations[id - MENU_DURATION]);
+                    refreshUi();
                 }
                 return false;
         }
     }
 
-    @Override
-    public void onRegionTapped(int region) {
-        if (mMemRegion != region) {
-            mMemRegion = region;
-            refreshStats();
-        }
-    }
-
-    private void addNotAvailableMessage() {
-        Preference notAvailable = new Preference(getActivity());
-        notAvailable.setTitle(R.string.power_usage_not_available);
-        mAppListGroup.addPreference(notAvailable);
-    }
-
     /**
      * All states in which we consider a process to be actively running (rather than
      * something that can be freely killed to reclaim RAM).  Note this also includes
@@ -396,385 +351,75 @@
             ProcessStats.STATE_CACHED_EMPTY
     };
 
-    public static final int[] RED_MEM_STATES = new int[] {
-            ProcessStats.ADJ_MEM_FACTOR_CRITICAL
-    };
-
-    public static final int[] YELLOW_MEM_STATES = new int[] {
-            ProcessStats.ADJ_MEM_FACTOR_CRITICAL, ProcessStats.ADJ_MEM_FACTOR_LOW,
-            ProcessStats.ADJ_MEM_FACTOR_MODERATE
-    };
-
-    private String makeDuration(long time) {
+    public static String makeDuration(long time) {
         StringBuilder sb = new StringBuilder(32);
         TimeUtils.formatDuration(time, sb);
         return sb.toString();
     }
 
-    private void refreshStats() {
+    private void refreshUi() {
         updateMenus();
 
-        if (mStats == null || mLastDuration != mDuration) {
-            load();
-        }
-
-        int[] stats;
-        int statsLabel;
-        if (mStatsType == MENU_TYPE_FOREGROUND) {
-            stats = FOREGROUND_PROC_STATES;
-            statsLabel = R.string.process_stats_type_foreground;
-        } else if (mStatsType == MENU_TYPE_CACHED) {
-            stats = CACHED_PROC_STATES;
-            statsLabel = R.string.process_stats_type_cached;
-        } else {
-            stats = mShowSystem ? BACKGROUND_AND_SYSTEM_PROC_STATES
-                    : ProcessStats.BACKGROUND_PROC_STATES;
-            statsLabel = R.string.process_stats_type_background;
-        }
 
         mAppListGroup.removeAll();
         mAppListGroup.setOrderingAsAdded(false);
+        mHeader.setOrder(-1);
+        mAppListGroup.addPreference(mHeader);
 
-        final long elapsedTime = mStats.mTimePeriodEndRealtime-mStats.mTimePeriodStartRealtime;
+        final long elapsedTime = mStatsManager.getElapsedTime();
 
-        long now = SystemClock.uptimeMillis();
-
-        final PackageManager pm = getActivity().getPackageManager();
-
-        mTotalTime = ProcessStats.dumpSingleTime(null, null, mStats.mMemFactorDurations,
-                mStats.mMemFactor, mStats.mStartTime, now);
-        if (DEBUG) Log.d(TAG, "Total time of stats: " + makeDuration(mTotalTime));
-
-        for (int i=0; i<mMemTimes.length; i++) {
-            mMemTimes[i] = 0;
-        }
-        for (int iscreen=0; iscreen<ProcessStats.ADJ_COUNT; iscreen+=ProcessStats.ADJ_SCREEN_MOD) {
-            for (int imem=0; imem<ProcessStats.ADJ_MEM_FACTOR_COUNT; imem++) {
-                int state = imem+iscreen;
-                mMemTimes[imem] += mStats.mMemFactorDurations[state];
-            }
-        }
-
-        long memTotalTime;
-        int[] memStates;
-
-        LinearColorPreference colors = new LinearColorPreference(getActivity());
-        colors.setOrder(-1);
-        switch (mMemRegion) {
-            case LinearColorBar.REGION_RED:
-                memTotalTime = mMemTimes[ProcessStats.ADJ_MEM_FACTOR_CRITICAL];
-                memStates = RED_MEM_STATES;
-                break;
-            case LinearColorBar.REGION_YELLOW:
-                memTotalTime = mMemTimes[ProcessStats.ADJ_MEM_FACTOR_CRITICAL]
-                        + mMemTimes[ProcessStats.ADJ_MEM_FACTOR_LOW]
-                        + mMemTimes[ProcessStats.ADJ_MEM_FACTOR_MODERATE];
-                memStates = YELLOW_MEM_STATES;
-                break;
-            default:
-                memTotalTime = mTotalTime;
-                memStates = ProcessStats.ALL_MEM_ADJ;
-                break;
-        }
+        memTotalTime = mTotalTime;
         final Context context = getActivity();
-        colors.setColors(context.getColor(R.color.running_processes_apps_ram),
+        // TODO: More Colors.
+        mColors.setColors(context.getColor(R.color.running_processes_apps_ram),
                 context.getColor(R.color.running_processes_apps_ram),
                 context.getColor(R.color.running_processes_free_ram));
 
-        // Compute memory badness for chart color.
-        /*
-        int[] badColors = com.android.settings.Utils.BADNESS_COLORS;
-        long timeGood = mMemTimes[ProcessStats.ADJ_MEM_FACTOR_NORMAL];
-        timeGood += (mMemTimes[ProcessStats.ADJ_MEM_FACTOR_MODERATE]*2)/3;
-        timeGood += mMemTimes[ProcessStats.ADJ_MEM_FACTOR_LOW]/3;
-        float memBadness = ((float)timeGood)/mTotalTime;
-        int badnessColor = badColors[1 + Math.round(memBadness*(badColors.length-2))];
-        colors.setColors(badnessColor, badnessColor, badnessColor);
-        */
-
-        // We are now going to scale the mMemTimes to match the total elapsed time.
-        // These are in uptime, so they will often be smaller than the elapsed time,
-        // but if the user taps on the bar we want to show the times to them.  It is confusing
-        // to see them be smaller than what we told them the measured duration is, so just
-        // scaling them up with make things look reasonable with them none the wiser.
-        for (int i=0; i<ProcessStats.ADJ_MEM_FACTOR_COUNT; i++) {
-            mMemTimes[i] = (long)((mMemTimes[i]*(double)elapsedTime)/mTotalTime);
-        }
-
-        ProcessStats.TotalMemoryUseCollection totalMem = new ProcessStats.TotalMemoryUseCollection(
-                ProcessStats.ALL_SCREEN_ADJ, memStates);
-        mStats.computeTotalMemoryUse(totalMem, now);
-        double freeWeight = totalMem.sysMemFreeWeight + totalMem.sysMemCachedWeight;
-        double usedWeight = totalMem.sysMemKernelWeight + totalMem.sysMemNativeWeight
-                + totalMem.sysMemZRamWeight;
-        double backgroundWeight = 0, persBackgroundWeight = 0;
-        mMemCachedWeight = totalMem.sysMemCachedWeight;
-        mMemFreeWeight = totalMem.sysMemFreeWeight;
-        mMemZRamWeight = totalMem.sysMemZRamWeight;
-        mMemKernelWeight = totalMem.sysMemKernelWeight;
-        mMemNativeWeight = totalMem.sysMemNativeWeight;
-        for (int i=0; i<ProcessStats.STATE_COUNT; i++) {
-            if (i == ProcessStats.STATE_SERVICE_RESTARTING) {
-                // These don't really run.
-                mMemStateWeights[i] = 0;
-            } else {
-                mMemStateWeights[i] = totalMem.processStateWeight[i];
-                if (i >= ProcessStats.STATE_HOME) {
-                    freeWeight += totalMem.processStateWeight[i];
-                } else {
-                    usedWeight += totalMem.processStateWeight[i];
-                }
-                if (i >= ProcessStats.STATE_IMPORTANT_FOREGROUND) {
-                    backgroundWeight += totalMem.processStateWeight[i];
-                    persBackgroundWeight += totalMem.processStateWeight[i];
-                }
-                if (i == ProcessStats.STATE_PERSISTENT) {
-                    persBackgroundWeight += totalMem.processStateWeight[i];
-                }
-            }
-        }
-        if (DEBUG) {
-            Log.i(TAG, "Used RAM: " + Formatter.formatShortFileSize(getActivity(),
-                    (long)((usedWeight * 1024) / memTotalTime)));
-            Log.i(TAG, "Free RAM: " + Formatter.formatShortFileSize(getActivity(),
-                    (long)((freeWeight * 1024) / memTotalTime)));
-            Log.i(TAG, "Total RAM: " + Formatter.formatShortFileSize(getActivity(),
-                    (long)(((freeWeight+usedWeight) * 1024) / memTotalTime)));
-            Log.i(TAG, "Background+Cached RAM: " + Formatter.formatShortFileSize(getActivity(),
-                    (long)((backgroundWeight * 1024) / memTotalTime)));
-        }
-        mMemTotalWeight = freeWeight + usedWeight;
-
         // For computing the ratio to show, we want to count the baseline cached RAM we
         // need (at which point we start killing processes) as used RAM, so that if we
         // reach the point of thrashing due to no RAM for any background processes we
         // report that as RAM being full.  To do this, we need to first convert the weights
         // back to actual RAM...  and since the RAM values we compute here won't exactly
         // match the real physical RAM, scale those to the actual physical RAM.  No problem!
-        double usedRam = (usedWeight*1024)/memTotalTime;
-        double freeRam = (freeWeight*1024)/memTotalTime;
-        double totalRam = usedRam + freeRam;
-        MemInfoReader memReader = new MemInfoReader();
-        memReader.readMemInfo();
-        double realTotalRam = memReader.getTotalSize();
-        double totalScale = realTotalRam / totalRam;
-        mWeightToRam = totalScale / memTotalTime * 1024;
-        mMaxWeight = totalRam / mWeightToRam;
-        double realUsedRam = usedRam * totalScale;
-        double realFreeRam = freeRam * totalScale;
-        if (DEBUG) {
-            Log.i(TAG, "Scaled Used RAM: " + Formatter.formatShortFileSize(getActivity(),
-                    (long)realUsedRam));
-            Log.i(TAG, "Scaled Free RAM: " + Formatter.formatShortFileSize(getActivity(),
-                    (long)realFreeRam));
-        }
-        ActivityManager.MemoryInfo memInfo = new ActivityManager.MemoryInfo();
-        ((ActivityManager)getActivity().getSystemService(Context.ACTIVITY_SERVICE)).getMemoryInfo(
-                memInfo);
-        long baseCacheRam;
-        if (memInfo.hiddenAppThreshold >= realFreeRam) {
-            realUsedRam = realFreeRam;
-            realFreeRam = 0;
-            baseCacheRam = (long)realFreeRam;
-        } else {
-            realUsedRam += memInfo.hiddenAppThreshold;
-            realFreeRam -= memInfo.hiddenAppThreshold;
-            baseCacheRam = memInfo.hiddenAppThreshold;
-        }
-        if (DEBUG) {
-            Log.i(TAG, "Adj Scaled Used RAM: " + Formatter.formatShortFileSize(getActivity(),
-                    (long)realUsedRam));
-            Log.i(TAG, "Adj Scaled Free RAM: " + Formatter.formatShortFileSize(getActivity(),
-                    (long)realFreeRam));
-        }
+        MemInfo memInfo = mStatsManager.getMemInfo();
 
-        mMemStatusPref.setOrder(-2);
-        mAppListGroup.addPreference(mMemStatusPref);
-        String durationString = Utils.formatElapsedTime(getActivity(), elapsedTime, false);
-        String usedString = Formatter.formatShortFileSize(getActivity(), (long) realUsedRam);
-        String totalString = Formatter.formatShortFileSize(getActivity(), (long)realTotalRam);
+        String durationString = Utils.formatElapsedTime(context, elapsedTime, false);
+        String usedString = Formatter.formatShortFileSize(context, (long) memInfo.realUsedRam);
+        String totalString = Formatter.formatShortFileSize(context, (long) memInfo.realTotalRam);
         CharSequence memString;
         CharSequence[] memStatesStr = getResources().getTextArray(R.array.ram_states);
-        if (mMemState >= 0 && mMemState < memStatesStr.length) {
-            memString = memStatesStr[mMemState];
+        int memState = mStatsManager.getMemState();
+        if (memState >= 0 && memState < memStatesStr.length) {
+            memString = memStatesStr[memState];
         } else {
             memString = "?";
         }
-        mMemStatusPref.setTitle(getActivity().getString(R.string.process_stats_total_duration,
-                usedString, totalString, durationString));
-        mMemStatusPref.setSummary(getActivity().getString(R.string.process_stats_memory_status,
-                        memString)); 
-        float usedRatio = (float)(realUsedRam/(realFreeRam+realUsedRam));
-        colors.setRatios(usedRatio, 0, 1-usedRatio);
-
-        if (false) {
-            colors.setOnRegionTappedListener(this);
-            switch (mMemRegion) {
-                case LinearColorBar.REGION_RED:
-                    colors.setColoredRegions(LinearColorBar.REGION_RED);
-                    memTotalTime = mMemTimes[ProcessStats.ADJ_MEM_FACTOR_CRITICAL];
-                    memStates = RED_MEM_STATES;
-                    break;
-                case LinearColorBar.REGION_YELLOW:
-                    colors.setColoredRegions(LinearColorBar.REGION_RED
-                            | LinearColorBar.REGION_YELLOW);
-                    memTotalTime = mMemTimes[ProcessStats.ADJ_MEM_FACTOR_CRITICAL]
-                            + mMemTimes[ProcessStats.ADJ_MEM_FACTOR_LOW]
-                            + mMemTimes[ProcessStats.ADJ_MEM_FACTOR_MODERATE];
-                    memStates = YELLOW_MEM_STATES;
-                    break;
-                default:
-                    colors.setColoredRegions(LinearColorBar.REGION_ALL);
-                    memTotalTime = mTotalTime;
-                    memStates = ProcessStats.ALL_MEM_ADJ;
-                    break;
-            }
-            colors.setRatios(mMemTimes[ProcessStats.ADJ_MEM_FACTOR_CRITICAL] / (float)mTotalTime,
-                    (mMemTimes[ProcessStats.ADJ_MEM_FACTOR_LOW]
-                            + mMemTimes[ProcessStats.ADJ_MEM_FACTOR_MODERATE]) / (float)mTotalTime,
-                    mMemTimes[ProcessStats.ADJ_MEM_FACTOR_NORMAL] / (float)mTotalTime);
+        if (mShowPercentage) {
+            mMemUsed.setText(context.getString(
+                    R.string.process_stats_total_duration_percentage,
+                    Utils.formatPercentage((long) memInfo.realUsedRam, (long) memInfo.realTotalRam),
+                    durationString));
+        } else {
+            mMemUsed.setText(context.getString(R.string.process_stats_total_duration,
+                    usedString, totalString, durationString));
         }
+        mMemStatus.setText(context.getString(R.string.process_stats_memory_status,
+                        memString));
+        float usedRatio = (float)(memInfo.realUsedRam
+                / (memInfo.realFreeRam + memInfo.realUsedRam));
+        mColors.setRatios(usedRatio, 0, 1-usedRatio);
 
-        mAppListGroup.addPreference(colors);
+        List<ProcStatsPackageEntry> pkgEntries = mStatsManager.getEntries();
 
-        ProcessStats.ProcessDataCollection bgTotals = new ProcessStats.ProcessDataCollection(
-                ProcessStats.ALL_SCREEN_ADJ, memStates, stats);
-        ProcessStats.ProcessDataCollection runTotals = new ProcessStats.ProcessDataCollection(
-                ProcessStats.ALL_SCREEN_ADJ, memStates, ProcessStats.NON_CACHED_PROC_STATES);
-
-        final ArrayList<ProcStatsEntry> procEntries = new ArrayList<>();
-        final ArrayList<ProcStatsPackageEntry> pkgEntries = new ArrayList<>();
-
-        /*
-        ArrayList<ProcessStats.ProcessState> rawProcs = mStats.collectProcessesLocked(
-                ProcessStats.ALL_SCREEN_ADJ, ProcessStats.ALL_MEM_ADJ,
-                ProcessStats.BACKGROUND_PROC_STATES, now, null);
-        for (int i=0, N=(rawProcs != null ? rawProcs.size() : 0); i<N; i++) {
-            procs.add(new ProcStatsEntry(rawProcs.get(i), bgTotals));
-        }
-        */
-
-        if (DEBUG) Log.d(TAG, "-------------------- PULLING PROCESSES");
-
-        final ProcessMap<ProcStatsEntry> entriesMap = new ProcessMap<ProcStatsEntry>();
-        for (int ipkg=0, N=mStats.mPackages.getMap().size(); ipkg<N; ipkg++) {
-            final SparseArray<SparseArray<ProcessStats.PackageState>> pkgUids
-                    = mStats.mPackages.getMap().valueAt(ipkg);
-            for (int iu=0; iu<pkgUids.size(); iu++) {
-                final SparseArray<ProcessStats.PackageState> vpkgs = pkgUids.valueAt(iu);
-                for (int iv=0; iv<vpkgs.size(); iv++) {
-                    final ProcessStats.PackageState st = vpkgs.valueAt(iv);
-                    for (int iproc=0; iproc<st.mProcesses.size(); iproc++) {
-                        final ProcessStats.ProcessState pkgProc = st.mProcesses.valueAt(iproc);
-                        final ProcessStats.ProcessState proc = mStats.mProcesses.get(pkgProc.mName,
-                                pkgProc.mUid);
-                        if (proc == null) {
-                            Log.w(TAG, "No process found for pkg " + st.mPackageName
-                                    + "/" + st.mUid + " proc name " + pkgProc.mName);
-                            continue;
-                        }
-                        ProcStatsEntry ent = entriesMap.get(proc.mName, proc.mUid);
-                        if (ent == null) {
-                            ent = new ProcStatsEntry(proc, st.mPackageName, bgTotals, runTotals,
-                                    mUseUss);
-                            if (ent.mRunWeight > 0) {
-                                if (DEBUG) Log.d(TAG, "Adding proc " + proc.mName + "/"
-                                        + proc.mUid + ": time=" + makeDuration(ent.mRunDuration) + " ("
-                                        + ((((double)ent.mRunDuration) / memTotalTime) * 100) + "%)"
-                                        + " pss=" + ent.mAvgRunMem);
-                                entriesMap.put(proc.mName, proc.mUid, ent);
-                                procEntries.add(ent);
-                            }
-                        }  else {
-                            ent.addPackage(st.mPackageName);
-                        }
-                    }
-                }
-            }
-        }
-
-        if (DEBUG) Log.d(TAG, "-------------------- MAPPING SERVICES");
-
-        // Add in service info.
-        if (mStatsType == MENU_TYPE_BACKGROUND) {
-            for (int ip=0, N=mStats.mPackages.getMap().size(); ip<N; ip++) {
-                SparseArray<SparseArray<ProcessStats.PackageState>> uids
-                        = mStats.mPackages.getMap().valueAt(ip);
-                for (int iu=0; iu<uids.size(); iu++) {
-                    SparseArray<ProcessStats.PackageState> vpkgs = uids.valueAt(iu);
-                    for (int iv=0; iv<vpkgs.size(); iv++) {
-                        ProcessStats.PackageState ps = vpkgs.valueAt(iv);
-                        for (int is=0, NS=ps.mServices.size(); is<NS; is++) {
-                            ProcessStats.ServiceState ss = ps.mServices.valueAt(is);
-                            if (ss.mProcessName != null) {
-                                ProcStatsEntry ent = entriesMap.get(ss.mProcessName,
-                                        uids.keyAt(iu));
-                                if (ent != null) {
-                                    if (DEBUG) Log.d(TAG, "Adding service " + ps.mPackageName
-                                            + "/" + ss.mName + "/" + uids.keyAt(iu) + " to proc "
-                                            + ss.mProcessName);
-                                    ent.addService(ss);
-                                } else {
-                                    Log.w(TAG, "No process " + ss.mProcessName + "/" + uids.keyAt(iu)
-                                            + " for service " + ss.mName);
-                                }
-                            }
-                        }
-                    }
-                }
-            }
-        }
-
-        // Combine processes into packages.
-        HashMap<String, ProcStatsPackageEntry> pkgMap = new HashMap<>();
-        for (int i=procEntries.size()-1; i>=0; i--) {
-            ProcStatsEntry proc = procEntries.get(i);
-            proc.evaluateTargetPackage(pm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
-            ProcStatsPackageEntry pkg = pkgMap.get(proc.mBestTargetPackage);
-            if (pkg == null) {
-                pkg = new ProcStatsPackageEntry(proc.mBestTargetPackage);
-                pkgMap.put(proc.mBestTargetPackage, pkg);
-                pkgEntries.add(pkg);
-            }
-            pkg.addEntry(proc);
-        }
-
-        // Add in fake entry representing the OS itself.
-        ProcStatsPackageEntry osPkg = new ProcStatsPackageEntry("os");
-        pkgMap.put("os", osPkg);
-        pkgEntries.add(osPkg);
-        ProcStatsEntry osEntry;
-        if (totalMem.sysMemNativeWeight > 0) {
-            osEntry = new ProcStatsEntry("os", 0,
-                    getString(R.string.process_stats_os_native), memTotalTime,
-                    (long)(totalMem.sysMemNativeWeight/memTotalTime));
-            osEntry.evaluateTargetPackage(pm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
-            osPkg.addEntry(osEntry);
-        }
-        if (totalMem.sysMemKernelWeight > 0) {
-            osEntry = new ProcStatsEntry("os", 0,
-                    getString(R.string.process_stats_os_kernel), memTotalTime,
-                    (long)(totalMem.sysMemKernelWeight/memTotalTime));
-            osEntry.evaluateTargetPackage(pm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
-            osPkg.addEntry(osEntry);
-        }
-        if (totalMem.sysMemZRamWeight > 0) {
-            osEntry = new ProcStatsEntry("os", 0,
-                    getString(R.string.process_stats_os_zram), memTotalTime,
-                    (long)(totalMem.sysMemZRamWeight/memTotalTime));
-            osEntry.evaluateTargetPackage(pm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
-            osPkg.addEntry(osEntry);
-        }
-        if (baseCacheRam > 0) {
-            osEntry = new ProcStatsEntry("os", 0,
-                    getString(R.string.process_stats_os_cache), memTotalTime, baseCacheRam/1024);
-            osEntry.evaluateTargetPackage(pm, mStats, bgTotals, runTotals, sEntryCompare, mUseUss);
-            osPkg.addEntry(osEntry);
-        }
-
+        // Update everything and get the absolute maximum of memory usage for scaling.
+        mMaxMemoryUsage = 0;
         for (int i=0, N=pkgEntries.size(); i<N; i++) {
             ProcStatsPackageEntry pkg = pkgEntries.get(i);
             pkg.updateMetrics();
+            float maxMem = Math.max(pkg.mMaxBgMem, pkg.mMaxRunMem);
+            if (maxMem > mMaxMemoryUsage) {
+                mMaxMemoryUsage = maxMem;
+            }
         }
 
         Collections.sort(pkgEntries, sPackageEntryCompare);
@@ -789,62 +434,25 @@
         int end = pkgEntries.size()-1;
         while (end >= 0) {
             ProcStatsPackageEntry pkg = pkgEntries.get(end);
-            final double percentOfWeight = (pkg.mRunWeight / mMaxWeight) * 100;
-            final double percentOfTime = (((double)pkg.mRunDuration) / memTotalTime) * 100;
+            final double percentOfWeight = (pkg.mRunWeight
+                    / (memInfo.totalRam / memInfo.weightToRam)) * 100;
+            final double percentOfTime = (((double) pkg.mRunDuration) / memTotalTime) * 100;
             if (percentOfWeight >= .01 || percentOfTime >= 25) {
                 break;
             }
             end--;
         }
-        for (int i=0; i<=end; i++) {
+        for (int i=0; i <= end; i++) {
             ProcStatsPackageEntry pkg = pkgEntries.get(i);
-            final double percentOfWeight = (pkg.mRunWeight / mMaxWeight) * 100;
-            final double percentOfTime = (((double)pkg.mRunDuration) / memTotalTime) * 100;
-            ProcessStatsPreference pref = new ProcessStatsPreference(getActivity());
-            pref.init(null, pkg);
-            pkg.retrieveUiData(getActivity(), pm);
-            pref.setTitle(pkg.mUiLabel);
-            if (pkg.mUiTargetApp != null) {
-                pref.setIcon(pkg.mUiTargetApp.loadIcon(pm));
-            }
+            ProcessStatsPreference pref = new ProcessStatsPreference(context);
+            pkg.retrieveUiData(context, mPm);
+            pref.init(pkg, mPm, mMaxMemoryUsage);
             pref.setOrder(i);
-            pref.setPercent(percentOfWeight, percentOfTime,
-                    (long)(pkg.mRunWeight * mWeightToRam));
             mAppListGroup.addPreference(pref);
-            if (mStatsType == MENU_TYPE_BACKGROUND) {
-                if (DEBUG) {
-                    Log.i(TAG, "App " + pkg.mUiLabel + ": weightedRam="
-                            + Formatter.formatShortFileSize(getActivity(),
-                                    (long)((pkg.mRunWeight * 1024) / memTotalTime))
-                            + ", avgRam=" + Formatter.formatShortFileSize(getActivity(),
-                                    (pkg.mAvgRunMem *1024)));
-                }
-
-            }
             if (mAppListGroup.getPreferenceCount() > (MAX_ITEMS_TO_LIST+1)) {
                 if (DEBUG) Log.d(TAG, "Done with UI, hit item limit!");
                 break;
             }
         }
     }
-
-    private void load() {
-        try {
-            mLastDuration = mDuration;
-            mMemState = mProcessStats.getCurrentMemoryState();
-            ParcelFileDescriptor pfd = mProcessStats.getStatsOverTime(mDuration);
-            mStats = new ProcessStats(false);
-            InputStream is = new ParcelFileDescriptor.AutoCloseInputStream(pfd);
-            mStats.read(is);
-            try {
-                is.close();
-            } catch (IOException e) {
-            }
-            if (mStats.mReadError != null) {
-                Log.w(TAG, "Failure reading process stats: " + mStats.mReadError);
-            }
-        } catch (RemoteException e) {
-            Log.e(TAG, "RemoteException:", e);
-        }
-    }
 }
