diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index d4e4926..f680d1f 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -266,6 +266,21 @@
             android:targetActivity="MobileNetworkSettings" />
 
         <!-- networks setting -->
+        <!-- "Choose network" screen. Used only when the Automatically
+             select network turned off-->
+        <activity android:name="NetworkSelectSettingActivity"
+            android:label="@string/choose_network_title"
+            android:theme="@style/NetworkOperatorsSettingsTheme"
+            android:configChanges="orientation|screenSize">
+            <intent-filter>
+                <action android:name="android.intent.action.VIEW" />
+                <action android:name="android.intent.action.MAIN" />
+                <action android:name="android.settings.NETWORK_OPERATOR_SETTINGS" />
+                <action android:name="android.settings.DATA_ROAMING_SETTINGS" />
+                <category android:name="android.intent.category.DEFAULT" />
+            </intent-filter>
+        </activity>
+
         <!-- service to handle network query requests sent to RIL -->
         <service android:name="NetworkQueryService" />
 
diff --git a/res/layout/choose_network.xml b/res/layout/choose_network.xml
new file mode 100644
index 0000000..2c327c56
--- /dev/null
+++ b/res/layout/choose_network.xml
@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2018 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.
+-->
+
+<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    android:id="@+id/choose_network_content"
+    android:layout_height="match_parent"
+    android:layout_width="match_parent">
+</FrameLayout>
\ No newline at end of file
diff --git a/res/layout/choose_network_progress_header.xml b/res/layout/choose_network_progress_header.xml
new file mode 100644
index 0000000..671c297
--- /dev/null
+++ b/res/layout/choose_network_progress_header.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+    Copyright (C) 2018 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.
+-->
+
+<FrameLayout
+    android:layout_width="match_parent"
+    android:layout_height="3dp"
+    xmlns:android="http://schemas.android.com/apk/res/android">
+    <View
+        android:id="@+id/progress_bar_background"
+        style="@style/TrimmedHorizontalProgressBar"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:background="?android:attr/colorSecondary" />
+    <ProgressBar
+        android:id="@+id/progress_bar_animation"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        style="@style/TrimmedHorizontalProgressBar"
+        android:indeterminate="true" />
+</FrameLayout>
\ No newline at end of file
diff --git a/res/layout/preference_category_no_label.xml b/res/layout/preference_category_no_label.xml
new file mode 100644
index 0000000..becfba7
--- /dev/null
+++ b/res/layout/preference_category_no_label.xml
@@ -0,0 +1,23 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+  Copyright (C) 2018 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.
+  -->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+       android:layout_width="match_parent"
+       android:layout_height="1dp"
+       android:background="?android:attr/dividerHorizontal"/>
+
+
diff --git a/res/values/strings.xml b/res/values/strings.xml
index c8af2f2..540876e 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -1183,8 +1183,14 @@
 
     <!-- RTT settings: used to turn on/off Real-Time Text, an accessibility feature similar to
          TTY that allows users to send text over a phone call. -->
-    <string name="rtt_mode_title">RTT</string>
-    <string name="rtt_mode_summary">Turn RTT on or off</string>
+    <string name="rtt_mode_title">Real-time text(RTT) call</string>
+    <string name="rtt_mode_summary">Allow messaging within a voice call</string>
+    <string name="rtt_mode_more_information">
+       RTT assists callers who are deaf, hard hearing, have a speech disability,
+       or need more than voice alone.<br/>
+       &lt;a href="<xliff:g example="http://www.google.com" id="url">http://support.google.com/mobile?p=telephony_rtt</xliff:g>">Learn more&lt;/a>
+       <br/> - RTT calls are saved as a message transcript
+       <br/> - RTT is not available for video calls</string>
 
     <!-- Service option entries.  -->
     <string-array name="tty_mode_entries">
diff --git a/res/xml/choose_network.xml b/res/xml/choose_network.xml
new file mode 100644
index 0000000..fdf2aae
--- /dev/null
+++ b/res/xml/choose_network.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2018 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.
+-->
+
+<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android"
+    android:title="@string/choose_network_title">
+
+    <PreferenceCategory
+        android:key="connected_network_operator_preference"/>
+
+    <PreferenceCategory
+        android:key="network_operators_preference"/>
+
+</PreferenceScreen>
\ No newline at end of file
diff --git a/res/xml/gsm_umts_options.xml b/res/xml/gsm_umts_options.xml
index e3e2617..3b4bc21 100644
--- a/res/xml/gsm_umts_options.xml
+++ b/res/xml/gsm_umts_options.xml
@@ -31,12 +31,19 @@
             android:key="button_network_select_key"
             android:title="@string/network_select_title"
             android:persistent="false"/>
+
+        <Preference
+            android:key="button_choose_network_key"
+            android:title="@string/choose_network_title"
+            android:fragment="com.android.phone.NetworkSelectSetting" />
     </com.android.phone.NetworkOperators>
 
     <!--We want separate APN setting from reset of settings because-->
     <!--we want user to change it with caution.-->
     <PreferenceCategory
-        android:key="category_gsm_apn_key">
+        android:key="category_gsm_apn_key"
+        android:layout="@layout/preference_category_no_label">
+
         <com.android.phone.RestrictedPreference
             android:key="button_gsm_apn_key"
             android:title="@string/apn_settings"
diff --git a/src/com/android/phone/CellInfoUtil.java b/src/com/android/phone/CellInfoUtil.java
new file mode 100644
index 0000000..c0409d8
--- /dev/null
+++ b/src/com/android/phone/CellInfoUtil.java
@@ -0,0 +1,169 @@
+/*
+ * Copyright (C) 2018 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.phone;
+
+import android.telephony.CellIdentity;
+import android.telephony.CellIdentityCdma;
+import android.telephony.CellIdentityGsm;
+import android.telephony.CellIdentityLte;
+import android.telephony.CellIdentityWcdma;
+import android.telephony.CellInfo;
+import android.telephony.CellInfoCdma;
+import android.telephony.CellInfoGsm;
+import android.telephony.CellInfoLte;
+import android.telephony.CellInfoWcdma;
+import android.telephony.TelephonyManager;
+import android.text.BidiFormatter;
+import android.text.TextDirectionHeuristics;
+import android.text.TextUtils;
+import android.util.Log;
+
+import com.android.internal.telephony.OperatorInfo;
+
+/**
+ * Add static Utility functions to get information from the CellInfo object.
+ * TODO: Modify {@link CellInfo} for simplify those functions
+ */
+public final class CellInfoUtil {
+    private static final String TAG = "NetworkSelectSetting";
+
+    private CellInfoUtil() {
+    }
+
+    /**
+     * Get the network type from a CellInfo. Network types include
+     * {@link TelephonyManager#NETWORK_TYPE_LTE}, {@link TelephonyManager#NETWORK_TYPE_UMTS},
+     * {@link TelephonyManager#NETWORK_TYPE_GSM}, {@link TelephonyManager#NETWORK_TYPE_CDMA} and
+     * {@link TelephonyManager#NETWORK_TYPE_UNKNOWN}
+     * @return network types
+     */
+    public static int getNetworkType(CellInfo cellInfo) {
+        if (cellInfo instanceof CellInfoLte) {
+            return TelephonyManager.NETWORK_TYPE_LTE;
+        } else if (cellInfo instanceof CellInfoWcdma) {
+            return TelephonyManager.NETWORK_TYPE_UMTS;
+        } else if (cellInfo instanceof CellInfoGsm) {
+            return TelephonyManager.NETWORK_TYPE_GSM;
+        } else if (cellInfo instanceof CellInfoCdma) {
+            return TelephonyManager.NETWORK_TYPE_CDMA;
+        } else {
+            Log.e(TAG, "Invalid CellInfo type");
+            return TelephonyManager.NETWORK_TYPE_UNKNOWN;
+        }
+    }
+
+    /**
+     * Get signal level as an int from 0..4.
+     * @return Signal strength level
+     */
+    public static int getLevel(CellInfo cellInfo) {
+        if (cellInfo instanceof CellInfoLte) {
+            return ((CellInfoLte) cellInfo).getCellSignalStrength().getLevel();
+        } else if (cellInfo instanceof CellInfoWcdma) {
+            return ((CellInfoWcdma) cellInfo).getCellSignalStrength().getLevel();
+        } else if (cellInfo instanceof CellInfoGsm) {
+            return ((CellInfoGsm) cellInfo).getCellSignalStrength().getLevel();
+        } else if (cellInfo instanceof CellInfoCdma) {
+            return ((CellInfoCdma) cellInfo).getCellSignalStrength().getLevel();
+        } else {
+            Log.e(TAG, "Invalid CellInfo type");
+            return 0;
+        }
+    }
+
+    /**
+     * Wrap a CellIdentity into a CellInfo.
+     */
+    public static CellInfo wrapCellInfoWithCellIdentity(CellIdentity cellIdentity) {
+        if (cellIdentity instanceof CellIdentityLte) {
+            CellInfoLte cellInfo = new CellInfoLte();
+            cellInfo.setCellIdentity((CellIdentityLte) cellIdentity);
+            return cellInfo;
+        } else if (cellIdentity instanceof CellIdentityCdma) {
+            CellInfoCdma cellInfo = new CellInfoCdma();
+            cellInfo.setCellIdentity((CellIdentityCdma) cellIdentity);
+            return cellInfo;
+        }  else if (cellIdentity instanceof CellIdentityWcdma) {
+            CellInfoWcdma cellInfo = new CellInfoWcdma();
+            cellInfo.setCellIdentity((CellIdentityWcdma) cellIdentity);
+            return cellInfo;
+        } else if (cellIdentity instanceof CellIdentityGsm) {
+            CellInfoGsm cellInfo = new CellInfoGsm();
+            cellInfo.setCellIdentity((CellIdentityGsm) cellIdentity);
+            return cellInfo;
+        } else {
+            Log.e(TAG, "Invalid CellInfo type");
+            return null;
+        }
+    }
+
+    /**
+     * Returns the title of the network obtained in the manual search.
+     *
+     * @param cellInfo contains the information of the network.
+     * @return Long Name if not null/empty, otherwise Short Name if not null/empty,
+     * else MCCMNC string.
+     */
+    public static String getNetworkTitle(CellInfo cellInfo) {
+        OperatorInfo oi = getOperatorInfoFromCellInfo(cellInfo);
+
+        if (!TextUtils.isEmpty(oi.getOperatorAlphaLong())) {
+            return oi.getOperatorAlphaLong();
+        } else if (!TextUtils.isEmpty(oi.getOperatorAlphaShort())) {
+            return oi.getOperatorAlphaShort();
+        } else {
+            BidiFormatter bidiFormatter = BidiFormatter.getInstance();
+            return bidiFormatter.unicodeWrap(oi.getOperatorNumeric(), TextDirectionHeuristics.LTR);
+        }
+    }
+
+    /**
+     * Wrap a cell info into an operator info.
+     */
+    public static OperatorInfo getOperatorInfoFromCellInfo(CellInfo cellInfo) {
+        OperatorInfo oi;
+        if (cellInfo instanceof CellInfoLte) {
+            CellInfoLte lte = (CellInfoLte) cellInfo;
+            oi = new OperatorInfo(
+                    (String) lte.getCellIdentity().getOperatorAlphaLong(),
+                    (String) lte.getCellIdentity().getOperatorAlphaShort(),
+                    lte.getCellIdentity().getMobileNetworkOperator());
+        } else if (cellInfo instanceof CellInfoWcdma) {
+            CellInfoWcdma wcdma = (CellInfoWcdma) cellInfo;
+            oi = new OperatorInfo(
+                    (String) wcdma.getCellIdentity().getOperatorAlphaLong(),
+                    (String) wcdma.getCellIdentity().getOperatorAlphaShort(),
+                    wcdma.getCellIdentity().getMobileNetworkOperator());
+        } else if (cellInfo instanceof CellInfoGsm) {
+            CellInfoGsm gsm = (CellInfoGsm) cellInfo;
+            oi = new OperatorInfo(
+                    (String) gsm.getCellIdentity().getOperatorAlphaLong(),
+                    (String) gsm.getCellIdentity().getOperatorAlphaShort(),
+                    gsm.getCellIdentity().getMobileNetworkOperator());
+        } else if (cellInfo instanceof CellInfoCdma) {
+            CellInfoCdma cdma = (CellInfoCdma) cellInfo;
+            oi = new OperatorInfo(
+                    (String) cdma.getCellIdentity().getOperatorAlphaLong(),
+                    (String) cdma.getCellIdentity().getOperatorAlphaShort(),
+                    "" /* operator numeric */);
+        } else {
+            Log.e(TAG, "Invalid CellInfo type");
+            oi = new OperatorInfo("", "", "");
+        }
+        return oi;
+    }
+}
diff --git a/src/com/android/phone/NetworkOperatorPreference.java b/src/com/android/phone/NetworkOperatorPreference.java
new file mode 100644
index 0000000..f29c038
--- /dev/null
+++ b/src/com/android/phone/NetworkOperatorPreference.java
@@ -0,0 +1,127 @@
+/*
+ * Copyright (C) 2018 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.phone;
+
+import android.content.Context;
+import android.graphics.Color;
+import android.graphics.drawable.ColorDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.LayerDrawable;
+import android.preference.Preference;
+import android.telephony.CellInfo;
+import android.telephony.SignalStrength;
+import android.telephony.TelephonyManager;
+import android.util.Log;
+import android.view.Gravity;
+
+import com.android.settingslib.graph.SignalDrawable;
+
+/**
+ * A Preference represents a network operator in the NetworkSelectSetting fragment.
+ */
+public class NetworkOperatorPreference extends Preference {
+
+    private static final String TAG = "NetworkOperatorPref";
+    private static final boolean DBG = true;
+    // number of signal strength level
+    public static final int NUMBER_OF_LEVELS = SignalStrength.NUM_SIGNAL_STRENGTH_BINS;
+    private CellInfo mCellInfo;
+    private int mLevel = -1;
+
+    // The following constants are used to draw signal icon.
+    private static final Drawable EMPTY_DRAWABLE = new ColorDrawable(Color.TRANSPARENT);
+    private static final int NO_CELL_DATA_CONNECTED_ICON = 0;
+
+    public NetworkOperatorPreference(CellInfo cellinfo, Context context) {
+        super(context);
+        mCellInfo = cellinfo;
+        refresh();
+    }
+
+    public CellInfo getCellInfo() {
+        return mCellInfo;
+    }
+
+    /**
+     * Refresh the NetworkOperatorPreference by updating the title and the icon.
+     */
+    public void refresh() {
+        if (DBG) Log.d(TAG, "refresh the network: " + CellInfoUtil.getNetworkTitle(mCellInfo));
+        setTitle(CellInfoUtil.getNetworkTitle(mCellInfo));
+        int level = CellInfoUtil.getLevel(mCellInfo);
+        if (DBG) Log.d(TAG, "refresh level: " + String.valueOf(level));
+        if (mLevel != level) {
+            mLevel = level;
+            updateIcon(mLevel);
+        }
+    }
+
+    /**
+     * Update the icon according to the input signal strength level.
+     */
+    public void setIcon(int level) {
+        updateIcon(level);
+    }
+
+    private int getIconId(int networkType) {
+        if (networkType == TelephonyManager.NETWORK_TYPE_CDMA) {
+            return R.drawable.signal_strength_1x;
+        } else if (networkType == TelephonyManager.NETWORK_TYPE_LTE) {
+            return R.drawable.signal_strength_lte;
+        } else if (networkType == TelephonyManager.NETWORK_TYPE_UMTS) {
+            return R.drawable.signal_strength_3g;
+        } else if (networkType == TelephonyManager.NETWORK_TYPE_GSM) {
+            return R.drawable.signal_strength_g;
+        } else {
+            return 0;
+        }
+    }
+
+    private void updateIcon(int level) {
+        if (level < 0 || level >= NUMBER_OF_LEVELS) return;
+        Context context = getContext();
+        // Make the signal strength drawable
+        int iconId = 0;
+        if (DBG) Log.d(TAG, "updateIcon level: " + String.valueOf(level));
+        iconId = SignalDrawable.getState(level, NUMBER_OF_LEVELS, false /* cutOut */);
+
+        SignalDrawable signalDrawable = new SignalDrawable(getContext());
+        signalDrawable.setLevel(iconId);
+        signalDrawable.setDarkIntensity(0);
+
+        // Make the network type drawable
+        int iconType = getIconId(CellInfoUtil.getNetworkType(mCellInfo));
+        Drawable networkDrawable =
+                iconType == NO_CELL_DATA_CONNECTED_ICON
+                        ? EMPTY_DRAWABLE
+                        : getContext()
+                        .getResources().getDrawable(iconType, getContext().getTheme());
+
+        // Overlay the two drawables
+        Drawable[] layers = {networkDrawable, signalDrawable};
+        final int iconSize =
+                context.getResources().getDimensionPixelSize(R.dimen.signal_strength_icon_size);
+
+        LayerDrawable icons = new LayerDrawable(layers);
+        // Set the network type icon at the top left
+        icons.setLayerGravity(0 /* index of networkDrawable */, Gravity.TOP | Gravity.LEFT);
+        // Set the signal strength icon at the bottom right
+        icons.setLayerGravity(1 /* index of SignalDrawable */, Gravity.BOTTOM | Gravity.RIGHT);
+        icons.setLayerSize(1 /* index of SignalDrawable */, iconSize, iconSize);
+        setIcon(icons);
+    }
+}
diff --git a/src/com/android/phone/NetworkOperators.java b/src/com/android/phone/NetworkOperators.java
index c39937e..babd283 100644
--- a/src/com/android/phone/NetworkOperators.java
+++ b/src/com/android/phone/NetworkOperators.java
@@ -18,6 +18,7 @@
 
 import android.app.ProgressDialog;
 import android.content.Context;
+import android.content.Intent;
 import android.os.AsyncResult;
 import android.os.Handler;
 import android.os.Message;
@@ -51,6 +52,7 @@
     //String keys for preference lookup
     public static final String BUTTON_NETWORK_SELECT_KEY = "button_network_select_key";
     public static final String BUTTON_AUTO_SELECT_KEY = "button_auto_select_key";
+    public static final String BUTTON_CHOOSE_NETWORK_KEY = "button_choose_network_key";
     public static final String CATEGORY_NETWORK_OPERATORS_KEY = "network_operators_category_key";
 
     int mPhoneId = SubscriptionManager.INVALID_PHONE_INDEX;
@@ -59,10 +61,15 @@
     //preference objects
     private NetworkSelectListPreference mNetworkSelect;
     private TwoStatePreference mAutoSelect;
+    private Preference mChooseNetwork;
 
     private int mSubId;
     private ProgressDialog mProgressDialog;
 
+    // There's two sets of Auto-Select UI in this class. {@link mNetworkSelect} is used for all
+    // pre-Pixel 3 devices, while {@link mChooseNetwork} is used for all devices after Pixel3.
+    boolean mEnableNewManualSelectNetworkUI;
+
     public NetworkOperators(Context context, AttributeSet attrs) {
         super(context, attrs);
     }
@@ -75,10 +82,16 @@
      * Initialize NetworkOperators instance.
      */
     public void initialize() {
-        mNetworkSelect =
-                (NetworkSelectListPreference) findPreference(BUTTON_NETWORK_SELECT_KEY);
-        mAutoSelect =
-                (TwoStatePreference) findPreference(BUTTON_AUTO_SELECT_KEY);
+        mEnableNewManualSelectNetworkUI = getContext().getResources().getBoolean(
+                com.android.internal.R.bool.config_enableNewAutoSelectNetworkUI);
+        mAutoSelect = (TwoStatePreference) findPreference(BUTTON_AUTO_SELECT_KEY);
+        mChooseNetwork = findPreference(BUTTON_CHOOSE_NETWORK_KEY);
+        mNetworkSelect = (NetworkSelectListPreference) findPreference(BUTTON_NETWORK_SELECT_KEY);
+        if (mEnableNewManualSelectNetworkUI) {
+            this.removePreference(mNetworkSelect);
+        } else {
+            this.removePreference(mChooseNetwork);
+        }
         mProgressDialog = new ProgressDialog(getContext());
     }
 
@@ -96,10 +109,22 @@
             mAutoSelect.setOnPreferenceChangeListener(this);
         }
 
-        if (mNetworkSelect != null) {
-            mNetworkSelect.initialize(mSubId, queryService, this, mProgressDialog);
+        if (mEnableNewManualSelectNetworkUI) {
+            if (mChooseNetwork != null) {
+                TelephonyManager telephonyManager = (TelephonyManager)
+                        getContext().getSystemService(Context.TELEPHONY_SERVICE);
+                logd("data connection status " + telephonyManager.getDataState());
+                if (telephonyManager.getDataState() == telephonyManager.DATA_CONNECTED) {
+                    mChooseNetwork.setSummary(telephonyManager.getNetworkOperatorName());
+                } else {
+                    mChooseNetwork.setSummary(R.string.network_disconnected);
+                }
+            }
+        } else {
+            if (mNetworkSelect != null) {
+                mNetworkSelect.initialize(mSubId, queryService, this, mProgressDialog);
+            }
         }
-
         getNetworkSelectionMode();
     }
 
@@ -114,6 +139,7 @@
     public boolean onPreferenceChange(Preference preference, Object newValue) {
         if (preference == mAutoSelect) {
             boolean autoSelect = (Boolean) newValue;
+            logd("onPreferenceChange autoSelect: " + String.valueOf(autoSelect));
             selectNetworkAutomatic(autoSelect);
             MetricsLogger.action(getContext(),
                     MetricsEvent.ACTION_MOBILE_NETWORK_AUTO_SELECT_NETWORK_TOGGLE, autoSelect);
@@ -156,8 +182,14 @@
                             if (mAutoSelect != null) {
                                 mAutoSelect.setChecked(autoSelect);
                             }
-                            if (mNetworkSelect != null) {
-                                mNetworkSelect.setEnabled(!autoSelect);
+                            if (mEnableNewManualSelectNetworkUI) {
+                                if (mChooseNetwork != null) {
+                                    mChooseNetwork.setEnabled(!autoSelect);
+                                }
+                            } else {
+                                if (mNetworkSelect != null) {
+                                    mNetworkSelect.setEnabled(!autoSelect);
+                                }
                             }
                         } catch (Exception e) {
                             if (DBG) loge("get network selection mode: unable to parse result.");
@@ -172,10 +204,9 @@
     // Used by both mAutoSelect and mNetworkSelect buttons.
     protected void displayNetworkSelectionFailed(Throwable ex) {
         String status;
-
         if ((ex != null && ex instanceof CommandException)
                 && ((CommandException) ex).getCommandError()
-                        == CommandException.Error.ILLEGAL_SIM_OR_ME) {
+                == CommandException.Error.ILLEGAL_SIM_OR_ME) {
             status = getContext().getResources().getString(R.string.not_allowed);
         } else {
             status = getContext().getResources().getString(R.string.connect_later);
@@ -210,9 +241,17 @@
     }
 
     private void selectNetworkAutomatic(boolean autoSelect) {
-        if (mNetworkSelect != null) {
-            mNetworkSelect.setEnabled(!autoSelect);
+        logd("selectNetworkAutomatic: " + String.valueOf(autoSelect));
+        if (mEnableNewManualSelectNetworkUI) {
+            if (mChooseNetwork != null) {
+                mChooseNetwork.setEnabled(!autoSelect);
+            }
+        } else {
+            if (mNetworkSelect != null) {
+                mNetworkSelect.setEnabled(!autoSelect);
+            }
         }
+
         if (autoSelect) {
             if (DBG) logd("select network automatically...");
             showAutoSelectProgressBar();
@@ -222,8 +261,17 @@
             if (phone != null) {
                 phone.setNetworkSelectionModeAutomatic(msg);
             }
-        } else if (mNetworkSelect != null) {
-            mNetworkSelect.onClick();
+        } else {
+            if (mEnableNewManualSelectNetworkUI) {
+                if (mChooseNetwork != null) {
+                    // Open the choose Network page automatically when user turn off the auto-select
+                    openChooseNetworkPage();
+                }
+            } else {
+                if (mNetworkSelect != null) {
+                    mNetworkSelect.onClick();
+                }
+            }
         }
     }
 
@@ -251,8 +299,24 @@
         mProgressDialog.show();
     }
 
+    /**
+     * Open the Choose netwotk page via {@alink NetworkSelectSettingActivity}
+     */
+    public void openChooseNetworkPage() {
+        Intent intent = NetworkSelectSettingActivity.getIntent(getContext(), mPhoneId);
+        getContext().startActivity(intent);
+    }
+
     protected boolean preferenceTreeClick(Preference preference) {
-        return (preference == mAutoSelect || preference == mNetworkSelect);
+        if (mEnableNewManualSelectNetworkUI) {
+            logd("enable New AutoSelectNetwork UI");
+            if (preference == mChooseNetwork) {
+                openChooseNetworkPage();
+            }
+            return (preference == mAutoSelect || preference == mChooseNetwork);
+        } else {
+            return (preference == mAutoSelect || preference == mNetworkSelect);
+        }
     }
 
     private void logd(String msg) {
@@ -262,4 +326,4 @@
     private void loge(String msg) {
         Log.e(LOG_TAG, "[NetworksList] " + msg);
     }
-}
+}
\ No newline at end of file
diff --git a/src/com/android/phone/NetworkSelectListPreference.java b/src/com/android/phone/NetworkSelectListPreference.java
index 146c76e..a8f29c9 100644
--- a/src/com/android/phone/NetworkSelectListPreference.java
+++ b/src/com/android/phone/NetworkSelectListPreference.java
@@ -411,7 +411,7 @@
                 String networkTitle = getNetworkTitle(cellInfo);
                 if (!networkEntriesList.contains(networkTitle)) {
                     networkEntriesList.add(networkTitle);
-                    networkEntryValuesList.add(Integer.toString(networkEntriesList.size() + 1));
+                    networkEntryValuesList.add(getOperatorNumeric(cellInfo));
                 }
             }
             setEntries(networkEntriesList.toArray(new CharSequence[networkEntriesList.size()]));
@@ -510,6 +510,16 @@
     }
 
     /**
+     * Returns the operator numeric (MCCMNC) obtained in the manual search.
+     *
+     * @param cellInfo contains the information of the network.
+     * @return MCCMNC string.
+     */
+    private String getOperatorNumeric(CellInfo cellInfo) {
+        return getOperatorInfoFromCellInfo(cellInfo).getOperatorNumeric();
+    }
+
+    /**
      * Wrap a cell info into an operator info.
      */
     private OperatorInfo getOperatorInfoFromCellInfo(CellInfo cellInfo) {
diff --git a/src/com/android/phone/NetworkSelectSetting.java b/src/com/android/phone/NetworkSelectSetting.java
new file mode 100644
index 0000000..7ef3dea
--- /dev/null
+++ b/src/com/android/phone/NetworkSelectSetting.java
@@ -0,0 +1,634 @@
+/*
+ * Copyright (C) 2018 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.phone;
+
+import android.app.Activity;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.Intent;
+import android.content.ServiceConnection;
+import android.metrics.LogMaker;
+import android.os.AsyncResult;
+import android.os.Bundle;
+import android.os.Handler;
+import android.os.IBinder;
+import android.os.Message;
+import android.os.RemoteException;
+import android.preference.Preference;
+import android.preference.PreferenceCategory;
+import android.preference.PreferenceFragment;
+import android.preference.PreferenceScreen;
+import android.telephony.AccessNetworkConstants;
+import android.telephony.CellIdentity;
+import android.telephony.CellInfo;
+import android.telephony.NetworkRegistrationState;
+import android.telephony.ServiceState;
+import android.telephony.SubscriptionManager;
+import android.telephony.TelephonyManager;
+import android.util.Log;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+
+import com.android.internal.logging.MetricsLogger;
+import com.android.internal.logging.nano.MetricsProto;
+import com.android.internal.telephony.OperatorInfo;
+import com.android.internal.telephony.Phone;
+import com.android.internal.telephony.PhoneFactory;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * "Choose network" settings UI for the Phone app.
+ */
+public class NetworkSelectSetting extends PreferenceFragment {
+
+    private static final String TAG = "NetworkSelectSetting";
+    private static final boolean DBG = true;
+
+    private static final int EVENT_NETWORK_SELECTION_DONE = 1;
+    private static final int EVENT_NETWORK_SCAN_RESULTS = 2;
+    private static final int EVENT_NETWORK_SCAN_ERROR = 3;
+    private static final int EVENT_NETWORK_SCAN_COMPLETED = 4;
+
+    private static final String PREF_KEY_CONNECTED_NETWORK_OPERATOR =
+            "connected_network_operator_preference";
+    private static final String PREF_KEY_NETWORK_OPERATORS = "network_operators_preference";
+
+    // used to add/remove NetworkOperatorsPreference.
+    private PreferenceCategory mNetworkOperatorsPreferences;
+    // used to add/remove connected NetworkOperatorPreference.
+    private PreferenceCategory mConnectedNetworkOperatorsPreference;
+    // manage the progress bar on the top of the page.
+    private View mProgressHeader;
+    private Preference mStatusMessagePreference;
+    private List<CellInfo> mCellInfoList;
+    private int mPhoneId = SubscriptionManager.INVALID_PHONE_INDEX;
+    private ViewGroup mFrameLayout;
+    private NetworkOperatorPreference mSelectedNetworkOperatorPreference;
+    private TelephonyManager mTelephonyManager;
+    private NetworkOperators mNetworkOperators;
+
+    private final Runnable mUpdateNetworkOperatorsRunnable = () -> {
+        updateNetworkOperatorsPreferenceCategory();
+    };
+
+    /**
+     * Create a new instance of this fragment.
+     */
+    public static NetworkSelectSetting newInstance(int phoneId) {
+        Bundle args = new Bundle();
+        args.putInt(NetworkSelectSettingActivity.KEY_PHONE_ID, phoneId);
+        NetworkSelectSetting fragment = new NetworkSelectSetting();
+        fragment.setArguments(args);
+
+        return fragment;
+    }
+
+    @Override
+    public void onCreate(Bundle icicle) {
+        logd("onCreate");
+        super.onCreate(icicle);
+
+        mPhoneId = getArguments().getInt(NetworkSelectSettingActivity.KEY_PHONE_ID);
+
+        addPreferencesFromResource(R.xml.choose_network);
+        mConnectedNetworkOperatorsPreference =
+                (PreferenceCategory) findPreference(PREF_KEY_CONNECTED_NETWORK_OPERATOR);
+        mNetworkOperatorsPreferences =
+                (PreferenceCategory) findPreference(PREF_KEY_NETWORK_OPERATORS);
+        mStatusMessagePreference = new Preference(getContext());
+        mSelectedNetworkOperatorPreference = null;
+        mTelephonyManager = (TelephonyManager)
+                getContext().getSystemService(Context.TELEPHONY_SERVICE);
+        mNetworkOperators = new NetworkOperators(getContext());
+        setRetainInstance(true);
+    }
+
+    @Override
+    public void onViewCreated(View view, Bundle savedInstanceState) {
+        logd("onViewCreated");
+        super.onViewCreated(view, savedInstanceState);
+
+        if (getListView() != null) {
+            getListView().setDivider(null);
+        }
+        // Inflate progress bar
+        final Activity activity = getActivity();
+        if (activity != null) {
+            mFrameLayout = activity.findViewById(R.id.choose_network_content);
+            final LayoutInflater inflater = activity.getLayoutInflater();
+            final View pinnedHeader =
+                    inflater.inflate(R.layout.choose_network_progress_header, mFrameLayout, false);
+            mFrameLayout.addView(pinnedHeader);
+            mFrameLayout.setVisibility(View.VISIBLE);
+            mProgressHeader = pinnedHeader.findViewById(R.id.progress_bar_animation);
+            setProgressBarVisible(false);
+        }
+        forceConfigConnectedNetworkOperatorsPreferenceCategory();
+    }
+
+    @Override
+    public void onStart() {
+        if (DBG) logd("onStart");
+        super.onStart();
+
+        // Bind the NetworkQueryService
+        bindNetworkQueryService();
+    }
+
+    /**
+     * Invoked on each preference click in this hierarchy, overrides
+     * PreferenceActivity's implementation.  Used to make sure we track the
+     * preference click events.
+     * Since the connected network operator is either faked (when no data connection) or already
+     * connected, we do not allow user to click the connected network operator.
+     */
+    @Override
+    public boolean onPreferenceTreeClick(PreferenceScreen preferenceScreen,
+                                         Preference preference) {
+        if (DBG) logd("User clicked the screen");
+        stopNetworkQuery();
+        setProgressBarVisible(false);
+        if (preference instanceof  NetworkOperatorPreference) {
+            // Refresh the last selected item in case users reselect network.
+            if (mSelectedNetworkOperatorPreference != null) {
+                mSelectedNetworkOperatorPreference.setSummary("");
+            }
+
+            mSelectedNetworkOperatorPreference = (NetworkOperatorPreference) preference;
+            CellInfo cellInfo = mSelectedNetworkOperatorPreference.getCellInfo();
+            if (DBG) logd("User click a NetworkOperatorPreference: " + cellInfo.toString());
+
+            // Send metrics event
+            final LogMaker logMaker = new LogMaker(
+                    MetricsProto.MetricsEvent.ACTION_MOBILE_NETWORK_MANUAL_SELECT_NETWORK)
+                    .setType(MetricsProto.MetricsEvent.TYPE_ACTION);
+            if (CellInfoUtil.getNetworkTitle(cellInfo) != null) {
+                // Since operator list is loaded dynamically from modem, we cannot know which
+                // network user chooses if we only record integer index of newValue. So a new tag
+                // and a string value (network) is added in this MetricsEvent.
+                logMaker.addTaggedData(MetricsProto.MetricsEvent.FIELD_MOBILE_NETWORK,
+                        CellInfoUtil.getNetworkTitle(cellInfo));
+            }
+            MetricsLogger.action(logMaker);
+
+            // Connect to the network
+            Message msg = mHandler.obtainMessage(EVENT_NETWORK_SELECTION_DONE);
+            Phone phone = PhoneFactory.getPhone(mPhoneId);
+            if (phone != null) {
+                if (DBG) {
+                    logd("Connect to the network: " + CellInfoUtil.getNetworkTitle(cellInfo));
+                }
+                // Set summary as "Connecting" to the selected network.
+                mSelectedNetworkOperatorPreference.setSummary(R.string.network_connecting);
+
+                // Set summary as "Disconnected" to the previously connected network
+                if (mConnectedNetworkOperatorsPreference.getPreferenceCount() > 0) {
+                    NetworkOperatorPreference connectedNetworkOperator = (NetworkOperatorPreference)
+                            (mConnectedNetworkOperatorsPreference.getPreference(0));
+                    if (!CellInfoUtil.getNetworkTitle(cellInfo).equals(
+                            CellInfoUtil.getNetworkTitle(connectedNetworkOperator.getCellInfo()))) {
+                        connectedNetworkOperator.setSummary(R.string.network_disconnected);
+                    }
+                }
+
+                // Select network manually via Phone
+                OperatorInfo operatorInfo = CellInfoUtil.getOperatorInfoFromCellInfo(cellInfo);
+                if (DBG) logd("manually selected network operator: " + operatorInfo.toString());
+                phone.selectNetworkManually(operatorInfo, true, msg);
+                setProgressBarVisible(true);
+                return true;
+            } else {
+                loge("Error selecting network. phone is null.");
+                mSelectedNetworkOperatorPreference = null;
+                return false;
+            }
+
+        } else {
+            preferenceScreen.setEnabled(false);
+            return false;
+        }
+    }
+
+    @Override
+    public void onAttach(Activity activity) {
+        super.onAttach(activity);
+        if (!(getActivity() instanceof NetworkSelectSettingActivity)) {
+            throw new IllegalStateException("Parent activity is not NetworkSelectSettingActivity");
+        }
+    }
+
+    @Override
+    public void onStop() {
+        super.onStop();
+        if (DBG) logd("onStop");
+        getView().removeCallbacks(mUpdateNetworkOperatorsRunnable);
+        stopNetworkQuery();
+        // Unbind the NetworkQueryService
+        unbindNetworkQueryService();
+    }
+
+    private final Handler mHandler = new Handler() {
+        @Override
+        public void handleMessage(Message msg) {
+            AsyncResult ar;
+            switch (msg.what) {
+                case EVENT_NETWORK_SELECTION_DONE:
+                    if (DBG) logd("network selection done: hide the progress header");
+                    setProgressBarVisible(false);
+
+                    ar = (AsyncResult) msg.obj;
+                    if (ar.exception != null) {
+                        mNetworkOperators.displayNetworkSelectionFailed(ar.exception);
+                        // Set summary as "Couldn't connect" to the selected network.
+                        mSelectedNetworkOperatorPreference.setSummary(
+                                R.string.network_could_not_connect);
+                    } else {
+                        if (DBG) logd("manual network selection: succeeded! ");
+                        mNetworkOperators.displayNetworkSelectionSucceeded(msg.arg1);
+                        // Set summary as "Connected" to the selected network.
+                        mSelectedNetworkOperatorPreference.setSummary(R.string.network_connected);
+                    }
+                    break;
+
+                case EVENT_NETWORK_SCAN_RESULTS:
+                    List<CellInfo> results = aggregateCellInfoList((List<CellInfo>) msg.obj);
+                    mCellInfoList = new ArrayList<>(results);
+                    if (DBG) logd("after aggregate: " + mCellInfoList.toString());
+                    if (mCellInfoList != null && mCellInfoList.size() != 0) {
+                        updateNetworkOperators();
+                    } else {
+                        addMessagePreference(R.string.empty_networks_list);
+                    }
+
+                    break;
+
+                case EVENT_NETWORK_SCAN_ERROR:
+                    int error = msg.arg1;
+                    if (DBG) logd("error while querying available networks " + error);
+                    stopNetworkQuery();
+                    addMessagePreference(R.string.network_query_error);
+                    break;
+
+                case EVENT_NETWORK_SCAN_COMPLETED:
+                    stopNetworkQuery();
+                    if (DBG) logd("scan complete");
+                    setProgressBarVisible(false);
+                    if (mCellInfoList == null) {
+                        // In case the scan timeout before getting any results
+                        addMessagePreference(R.string.empty_networks_list);
+                    }
+                    break;
+            }
+            return;
+        }
+    };
+
+    private void loadNetworksList() {
+        if (DBG) logd("load networks list...");
+        setProgressBarVisible(true);
+        try {
+            if (mNetworkQueryService != null) {
+                if (DBG) logd("start network query");
+                mNetworkQueryService
+                        .startNetworkQuery(mCallback, mPhoneId, true /* is incremental result */);
+            } else {
+                if (DBG) logd("unable to start network query, mNetworkQueryService is null");
+                addMessagePreference(R.string.network_query_error);
+            }
+        } catch (RemoteException e) {
+            loge("loadNetworksList: exception from startNetworkQuery " + e);
+            addMessagePreference(R.string.network_query_error);
+        }
+    }
+
+    /**
+     * This implementation of INetworkQueryServiceCallback is used to receive
+     * callback notifications from the network query service.
+     */
+    private final INetworkQueryServiceCallback mCallback = new INetworkQueryServiceCallback.Stub() {
+
+        /** Returns the scan results to the user, this callback will be called at lease one time. */
+        public void onResults(List<CellInfo> results) {
+            if (DBG) logd("get scan results.");
+            Message msg = mHandler.obtainMessage(EVENT_NETWORK_SCAN_RESULTS, results);
+            msg.sendToTarget();
+        }
+
+        /**
+         * Informs the user that the scan has stopped.
+         *
+         * This callback will be called when the scan is finished or cancelled by the user.
+         * The related NetworkScanRequest will be deleted after this callback.
+         */
+        public void onComplete() {
+            if (DBG) logd("network scan completed.");
+            Message msg = mHandler.obtainMessage(EVENT_NETWORK_SCAN_COMPLETED);
+            msg.sendToTarget();
+        }
+
+        /**
+         * Informs the user that there is some error about the scan.
+         *
+         * This callback will be called whenever there is any error about the scan, and the scan
+         * will be terminated. onComplete() will NOT be called.
+         */
+        public void onError(int error) {
+            if (DBG) logd("get onError callback with error code: " + error);
+            Message msg = mHandler.obtainMessage(EVENT_NETWORK_SCAN_ERROR, error, 0 /* arg2 */);
+            msg.sendToTarget();
+        }
+    };
+
+    /**
+     * Updates network operators from {@link INetworkQueryServiceCallback#onResults()}.
+     */
+    private void updateNetworkOperators() {
+        if (DBG) logd("updateNetworkOperators");
+        if (getActivity() != null) {
+            final View view = getView();
+            final Handler handler = view.getHandler();
+            if (handler != null && handler.hasCallbacks(mUpdateNetworkOperatorsRunnable)) {
+                return;
+            }
+            view.post(mUpdateNetworkOperatorsRunnable);
+        }
+    }
+
+    /**
+     * Update the currently available network operators list, which only contains the unregistered
+     * network operators. So if the device has no data and the network operator in the connected
+     * network operator category shows "Disconnected", it will also exist in the available network
+     * operator category for user to select. On the other hand, if the device has data and the
+     * network operator in the connected network operator category shows "Connected", it will not
+     * exist in the available network category.
+     */
+    private void updateNetworkOperatorsPreferenceCategory() {
+        mNetworkOperatorsPreferences.removeAll();
+
+        configConnectedNetworkOperatorsPreferenceCategory();
+        for (int index = 0; index < mCellInfoList.size(); index++) {
+            if (!mCellInfoList.get(index).isRegistered()) {
+                NetworkOperatorPreference pref =
+                        new NetworkOperatorPreference(mCellInfoList.get(index), getContext());
+                pref.setKey(CellInfoUtil.getNetworkTitle(mCellInfoList.get(index)));
+                pref.setOrder(index);
+                mNetworkOperatorsPreferences.addPreference(pref);
+            }
+        }
+    }
+
+    /**
+     * Config the connected network operator preference when the page was created. When user get
+     * into this page, the device might or might not have data connection.
+     *   - If the device has data:
+     *     1. use {@code ServiceState#getNetworkRegistrationStates()} to get the currently
+     *        registered cellIdentity, wrap it into a CellInfo;
+     *     2. set the signal strength level as strong;
+     *     3. use {@link TelephonyManager#getNetworkOperatorName()} to get the title of the
+     *        previously connected network operator, since the CellIdentity got from step 1 only has
+     *        PLMN.
+     *   - If the device has no data, we will remove the connected network operators list from the
+     *     screen.
+     */
+    private void forceConfigConnectedNetworkOperatorsPreferenceCategory() {
+        if (DBG) logd("Force config ConnectedNetworkOperatorsPreferenceCategory");
+        if (mTelephonyManager.getDataState() == mTelephonyManager.DATA_CONNECTED) {
+            // Try to get the network registration states
+            ServiceState ss = mTelephonyManager.getServiceStateForSubscriber(mPhoneId);
+            List<NetworkRegistrationState> networkList =
+                    ss.getNetworkRegistrationStates(AccessNetworkConstants.TransportType.WWAN);
+            if (networkList == null || networkList.size() == 0) {
+                loge("getNetworkRegistrationStates return null");
+                // Remove the connected network operators category
+                removeConnectedNetworkOperatorPreference();
+                return;
+            }
+            CellIdentity cellIdentity = networkList.get(0).getCellIdentity();
+            CellInfo cellInfo = CellInfoUtil.wrapCellInfoWithCellIdentity(cellIdentity);
+            if (cellInfo != null) {
+                if (DBG) logd("Currently registered cell: " + cellInfo.toString());
+                NetworkOperatorPreference pref =
+                        new NetworkOperatorPreference(cellInfo, getContext());
+                pref.setTitle(mTelephonyManager.getNetworkOperatorName());
+                pref.setSummary(R.string.network_connected);
+                // Update the signal strength icon, since the default signalStrength value would be
+                // zero (it would be quite confusing why the connected network has no signal)
+                pref.setIcon(NetworkOperatorPreference.NUMBER_OF_LEVELS - 1);
+
+                mConnectedNetworkOperatorsPreference.addPreference(pref);
+            } else {
+                loge("Invalid CellIfno: " + cellInfo.toString());
+                // Remove the connected network operators category
+                removeConnectedNetworkOperatorPreference();
+            }
+        } else {
+            if (DBG) logd("No currently registered cell");
+            // Remove the connected network operators category
+            removeConnectedNetworkOperatorPreference();
+        }
+    }
+
+    /**
+     * Configure the ConnectedNetworkOperatorsPreferenceCategory. The category only need to be
+     * configured if the category is currently empty or the operator network title of the previous
+     * connected network is different from the new one.
+     */
+    private void configConnectedNetworkOperatorsPreferenceCategory() {
+        if (DBG) logd("config ConnectedNetworkOperatorsPreferenceCategory");
+        // Remove the category if the CellInfo list is empty or does not have registered cell.
+        if (mCellInfoList.size() == 0) {
+            if (DBG) logd("empty cellinfo list");
+            removeConnectedNetworkOperatorPreference();
+        }
+        CellInfo connectedNetworkOperator = null;
+        for (CellInfo cellInfo: mCellInfoList) {
+            if (cellInfo.isRegistered()) {
+                connectedNetworkOperator = cellInfo;
+                break;
+            }
+        }
+        if (connectedNetworkOperator == null) {
+            if (DBG) logd("no registered network");
+            removeConnectedNetworkOperatorPreference();
+            return;
+        }
+
+        // config the category if it is empty.
+        if (mConnectedNetworkOperatorsPreference.getPreferenceCount() == 0) {
+            if (DBG) logd("ConnectedNetworkSelectList is empty, add one");
+            addConnectedNetworkOperatorPreference(connectedNetworkOperator);
+            return;
+        }
+        NetworkOperatorPreference previousConnectedNetworkOperator = (NetworkOperatorPreference)
+                (mConnectedNetworkOperatorsPreference.getPreference(0));
+
+        // config the category if the network title of the previous connected network is different
+        // from the new one.
+        String cTitle = CellInfoUtil.getNetworkTitle(connectedNetworkOperator);
+        String pTitle = CellInfoUtil.getNetworkTitle(
+                previousConnectedNetworkOperator.getCellInfo());
+        if (!cTitle.equals(pTitle)) {
+            if (DBG) logd("reconfig the category: connected network changed");
+            addConnectedNetworkOperatorPreference(connectedNetworkOperator);
+            return;
+        }
+        if (DBG) logd("same network operator is connected, only refresh the connected network");
+        // Otherwise same network operator is connected, only refresh the connected network
+        // operator preference (first and the only one in this category).
+        ((NetworkOperatorPreference) mConnectedNetworkOperatorsPreference.getPreference(0))
+                .refresh();
+        return;
+    }
+
+    /**
+     * Creates a Preference for the given {@link CellInfo} and adds it to the
+     * {@link #mConnectedNetworkOperatorsPreference}.
+     */
+    private void addConnectedNetworkOperatorPreference(CellInfo cellInfo) {
+        if (DBG) logd("addConnectedNetworkOperatorPreference");
+        // Remove the current ConnectedNetworkOperatorsPreference
+        removeConnectedNetworkOperatorPreference();
+        final NetworkOperatorPreference pref =
+                new NetworkOperatorPreference(cellInfo, getContext());
+        pref.setSummary(R.string.network_connected);
+        mConnectedNetworkOperatorsPreference.addPreference(pref);
+        PreferenceScreen preferenceScreen = getPreferenceScreen();
+        preferenceScreen.addPreference(mConnectedNetworkOperatorsPreference);
+    }
+
+    /** Removes all preferences and hide the {@link #mConnectedNetworkOperatorsPreference}. */
+    private void removeConnectedNetworkOperatorPreference() {
+        mConnectedNetworkOperatorsPreference.removeAll();
+        PreferenceScreen preferenceScreen = getPreferenceScreen();
+        preferenceScreen.removePreference(mConnectedNetworkOperatorsPreference);
+    }
+
+    protected void setProgressBarVisible(boolean visible) {
+        if (mProgressHeader != null) {
+            mProgressHeader.setVisibility(visible ? View.VISIBLE : View.GONE);
+        }
+    }
+
+    private void addMessagePreference(int messageId) {
+        if (DBG) logd("remove callback");
+        getView().removeCallbacks(mUpdateNetworkOperatorsRunnable);
+        setProgressBarVisible(false);
+        if (DBG) logd("addMessagePreference");
+        mStatusMessagePreference.setTitle(messageId);
+        removeConnectedNetworkOperatorPreference();
+        mNetworkOperatorsPreferences.removeAll();
+        mNetworkOperatorsPreferences.addPreference(mStatusMessagePreference);
+    }
+
+    /**
+     * The Scan results may contains several cell infos with different radio technologies and signal
+     * strength for one network operator. Aggregate the CellInfoList by retaining only the cell info
+     * with the strongest signal strength.
+     */
+    private List<CellInfo> aggregateCellInfoList(List<CellInfo> cellInfoList) {
+        if (DBG) logd("before aggregate: " + cellInfoList.toString());
+        Map<String, CellInfo> map = new HashMap<>();
+        for (CellInfo cellInfo: cellInfoList) {
+            String networkTitle = CellInfoUtil.getNetworkTitle(cellInfo);
+            if (cellInfo.isRegistered() || !map.containsKey(networkTitle)) {
+                map.put(networkTitle, cellInfo);
+            } else {
+                if (map.get(networkTitle).isRegistered()
+                        || CellInfoUtil.getLevel(map.get(networkTitle))
+                        > CellInfoUtil.getLevel(cellInfo)) {
+                    // Skip if the stored cellInfo is registered or has higher signal strength level
+                    continue;
+                }
+                // Otherwise replace it with the new CellInfo
+                map.put(networkTitle, cellInfo);
+            }
+        }
+        return new ArrayList<>(map.values());
+    }
+
+    /**
+     * Service connection code for the NetworkQueryService.
+     * Handles the work of binding to a local object so that we can make
+     * the appropriate service calls.
+     */
+
+    /** Local service interface */
+    private INetworkQueryService mNetworkQueryService = null;
+    /** Flag indicating whether we have called bind on the service. */
+    boolean mShouldUnbind;
+
+    /** Service connection */
+    private final ServiceConnection mNetworkQueryServiceConnection = new ServiceConnection() {
+
+        /** Handle the task of binding the local object to the service */
+        public void onServiceConnected(ComponentName className, IBinder service) {
+            if (DBG) logd("connection created, binding local service.");
+            mNetworkQueryService = ((NetworkQueryService.LocalBinder) service).getService();
+            // Load the network list only when the service is well connected.
+            loadNetworksList();
+        }
+
+        /** Handle the task of cleaning up the local binding */
+        public void onServiceDisconnected(ComponentName className) {
+            if (DBG) logd("connection disconnected, cleaning local binding.");
+            mNetworkQueryService = null;
+        }
+    };
+
+    private void bindNetworkQueryService() {
+        if (DBG) logd("bindNetworkQueryService");
+        getContext().bindService(new Intent(getContext(), NetworkQueryService.class).setAction(
+                NetworkQueryService.ACTION_LOCAL_BINDER),
+                mNetworkQueryServiceConnection, Context.BIND_AUTO_CREATE);
+        mShouldUnbind = true;
+    }
+
+    private void unbindNetworkQueryService() {
+        if (DBG) logd("unbindNetworkQueryService");
+        if (mShouldUnbind) {
+            if (DBG) logd("mShouldUnbind is true");
+            // unbind the service.
+            getContext().unbindService(mNetworkQueryServiceConnection);
+            mShouldUnbind = false;
+        }
+    }
+
+    private void stopNetworkQuery() {
+        // Stop the network query process
+        try {
+            if (mNetworkQueryService != null) {
+                if (DBG) logd("Stop network query");
+                mNetworkQueryService.stopNetworkQuery();
+                mNetworkQueryService.unregisterCallback(mCallback);
+            }
+        } catch (RemoteException e) {
+            loge("Exception from stopNetworkQuery " + e);
+        }
+    }
+
+    private void logd(String msg) {
+        Log.d(TAG, msg);
+    }
+
+    private void loge(String msg) {
+        Log.e(TAG, msg);
+    }
+}
diff --git a/src/com/android/phone/NetworkSelectSettingActivity.java b/src/com/android/phone/NetworkSelectSettingActivity.java
new file mode 100644
index 0000000..2f730ad
--- /dev/null
+++ b/src/com/android/phone/NetworkSelectSettingActivity.java
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2018 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.phone;
+
+import android.app.Activity;
+import android.app.Fragment;
+import android.app.FragmentManager;
+import android.content.Context;
+import android.content.Intent;
+import android.os.Bundle;
+import android.util.Log;
+
+
+/**
+ * Activity associated with NetworkSelectSetting fragment
+ */
+public class NetworkSelectSettingActivity extends Activity {
+    private static final String TAG = "NetworkSelectSettingActivity";
+    public static final String KEY_PHONE_ID = "phone_id";
+
+    /**
+     * Returns the Android Intent that led to this Activity being created.
+     */
+    public static Intent getIntent(Context context, int phoneId) {
+        Intent intent = new Intent(context, NetworkSelectSettingActivity.class);
+        intent.putExtra(KEY_PHONE_ID, phoneId);
+        return intent;
+    }
+
+    @Override
+    public void onCreate(Bundle savedState) {
+        Log.d(TAG, "onCreate()");
+        super.onCreate(savedState);
+        int phoneId = getIntent().getExtras().getInt(KEY_PHONE_ID);
+        setContentView(R.layout.choose_network);
+
+        FragmentManager fragmentManager = getFragmentManager();
+        Fragment fragment = fragmentManager.findFragmentById(R.id.choose_network_content);
+        if (fragment == null) {
+            fragmentManager.beginTransaction()
+                    .add(R.id.choose_network_content,
+                            NetworkSelectSetting.newInstance(phoneId), TAG)
+                    .commit();
+        }
+    }
+}
diff --git a/testapps/EmbmsServiceTestApp/src/com/android/phone/testapps/embmsmw/EmbmsSampleDownloadService.java b/testapps/EmbmsServiceTestApp/src/com/android/phone/testapps/embmsmw/EmbmsSampleDownloadService.java
index 7bd0f70..6ddebb8 100644
--- a/testapps/EmbmsServiceTestApp/src/com/android/phone/testapps/embmsmw/EmbmsSampleDownloadService.java
+++ b/testapps/EmbmsServiceTestApp/src/com/android/phone/testapps/embmsmw/EmbmsSampleDownloadService.java
@@ -31,8 +31,9 @@
 import android.os.ParcelFileDescriptor;
 import android.os.RemoteException;
 import android.telephony.MbmsDownloadSession;
+import android.telephony.mbms.DownloadProgressListener;
 import android.telephony.mbms.DownloadRequest;
-import android.telephony.mbms.DownloadStateCallback;
+import android.telephony.mbms.DownloadStatusListener;
 import android.telephony.mbms.FileInfo;
 import android.telephony.mbms.FileServiceInfo;
 import android.telephony.mbms.MbmsDownloadSessionCallback;
@@ -143,9 +144,16 @@
         }
 
         @Override
-        public int registerStateCallback(DownloadRequest downloadRequest,
-                DownloadStateCallback callback) throws RemoteException {
-            mDownloadStateCallbacks.put(downloadRequest, callback);
+        public int addStatusListener(DownloadRequest downloadRequest,
+                DownloadStatusListener callback) throws RemoteException {
+            mDownloadStatusCallbacks.put(downloadRequest, callback);
+            return MbmsErrors.SUCCESS;
+        }
+
+        @Override
+        public int addProgressListener(DownloadRequest downloadRequest,
+                DownloadProgressListener callback) throws RemoteException {
+            mDownloadProgressCallbacks.put(downloadRequest, callback);
             return MbmsErrors.SUCCESS;
         }
 
@@ -183,7 +191,9 @@
     // A map of app-identifiers to (maps of service-ids to sets of temp file uris in use)
     private final Map<FrontendAppIdentifier, Map<String, Set<Uri>>> mTempFilesInUse =
             new ConcurrentHashMap<>();
-    private final Map<DownloadRequest, DownloadStateCallback> mDownloadStateCallbacks =
+    private final Map<DownloadRequest, DownloadStatusListener> mDownloadStatusCallbacks =
+            new ConcurrentHashMap<>();
+    private final Map<DownloadRequest, DownloadProgressListener> mDownloadProgressCallbacks =
             new ConcurrentHashMap<>();
 
     private HandlerThread mHandlerThread;
@@ -334,13 +344,14 @@
             UriPathPair tempFile, FileInfo fileToDownload) {
         int result = MbmsDownloadSession.RESULT_SUCCESSFUL;
         // Test Callback
-        DownloadStateCallback c = mDownloadStateCallbacks.get(request);
-        if (c != null) {
-            c.onProgressUpdated(request, fileToDownload, 0, 10, 0, 10);
+        DownloadStatusListener statusListener = mDownloadStatusCallbacks.get(request);
+        DownloadProgressListener progressListener = mDownloadProgressCallbacks.get(request);
+        if (progressListener != null) {
+            progressListener.onProgressUpdated(request, fileToDownload, 0, 10, 0, 10);
         }
         // Test Callback
-        if (c != null) {
-            c.onStateUpdated(request, fileToDownload,
+        if (statusListener != null) {
+            statusListener.onStatusUpdated(request, fileToDownload,
                     MbmsDownloadSession.STATUS_ACTIVELY_DOWNLOADING);
         }
         try {
@@ -367,8 +378,8 @@
             result = MbmsDownloadSession.RESULT_CANCELLED;
         }
         // Test Callback
-        if (c != null) {
-            c.onProgressUpdated(request, fileToDownload, 10, 10, 10, 10);
+        if (progressListener != null) {
+            progressListener.onProgressUpdated(request, fileToDownload, 10, 10, 10, 10);
         }
         // Take a round-trip through the download request serialization to exercise it
         DownloadRequest request1 = DownloadRequest.Builder.fromSerializedRequest(
diff --git a/testapps/EmbmsTestDownloadApp/src/com/android/phone/testapps/embmsdownload/EmbmsTestDownloadApp.java b/testapps/EmbmsTestDownloadApp/src/com/android/phone/testapps/embmsdownload/EmbmsTestDownloadApp.java
index 76baf05..f77b4ac 100644
--- a/testapps/EmbmsTestDownloadApp/src/com/android/phone/testapps/embmsdownload/EmbmsTestDownloadApp.java
+++ b/testapps/EmbmsTestDownloadApp/src/com/android/phone/testapps/embmsdownload/EmbmsTestDownloadApp.java
@@ -27,8 +27,9 @@
 import android.support.v7.widget.RecyclerView;
 import android.telephony.MbmsDownloadSession;
 import android.telephony.SubscriptionManager;
+import android.telephony.mbms.DownloadProgressListener;
 import android.telephony.mbms.DownloadRequest;
-import android.telephony.mbms.DownloadStateCallback;
+import android.telephony.mbms.DownloadStatusListener;
 import android.telephony.mbms.FileInfo;
 import android.telephony.mbms.FileServiceInfo;
 import android.telephony.mbms.MbmsDownloadSessionCallback;
@@ -292,8 +293,8 @@
                         "No DownloadRequest Pending for progress...", Toast.LENGTH_SHORT).show();
                 return;
             }
-            mDownloadManager.registerStateCallback(req, sInstance.getMainThreadHandler()::post,
-                    new DownloadStateCallback(DownloadStateCallback.PROGRESS_UPDATES) {
+            mDownloadManager.addProgressListener(req, sInstance.getMainThreadHandler()::post,
+                    new DownloadProgressListener() {
                         @Override
                         public void onProgressUpdated(DownloadRequest request, FileInfo fileInfo,
                                 int currentDownloadSize, int fullDownloadSize,
@@ -303,16 +304,6 @@
                                             + " fd: " + fullDownloadSize, Toast.LENGTH_SHORT)
                                     .show();
                         }
-
-                        @Override
-                        public void onStateUpdated(DownloadRequest request, FileInfo fileInfo,
-                                @MbmsDownloadSession.DownloadStatus int state) {
-                            // only registered for state callback, this shouldn't happen!
-                            Toast.makeText(EmbmsTestDownloadApp.this,
-                                    "State ERROR: received state update for callback that didn't"
-                                            + " filter it",
-                                    Toast.LENGTH_SHORT).show();
-                        }
                     });
         });
 
@@ -330,21 +321,10 @@
                         "No DownloadRequest Pending for state...", Toast.LENGTH_SHORT).show();
                 return;
             }
-            mDownloadManager.registerStateCallback(req, sInstance.getMainThreadHandler()::post,
-                    new DownloadStateCallback(DownloadStateCallback.STATE_UPDATES) {
+            mDownloadManager.addStatusListener(req, sInstance.getMainThreadHandler()::post,
+                    new DownloadStatusListener() {
                         @Override
-                        public void onProgressUpdated(DownloadRequest request, FileInfo fileInfo,
-                                int currentDownloadSize, int fullDownloadSize,
-                                int currentDecodedSize, int fullDecodedSize) {
-                            // only registered for state callback, this shouldn't happen!
-                            Toast.makeText(EmbmsTestDownloadApp.this,
-                                    "Progress ERROR: received progress update for"
-                                            + " callback that didn't "
-                                            + "filter it", Toast.LENGTH_SHORT).show();
-                        }
-
-                        @Override
-                        public void onStateUpdated(DownloadRequest request, FileInfo fileInfo,
+                        public void onStatusUpdated(DownloadRequest request, FileInfo fileInfo,
                                 @MbmsDownloadSession.DownloadStatus int state) {
                             Toast.makeText(EmbmsTestDownloadApp.this,
                                     "State Updated (" + fileInfo + ") state: " + state,
@@ -367,8 +347,20 @@
                         "No DownloadRequest Pending for state...", Toast.LENGTH_SHORT).show();
                 return;
             }
-            mDownloadManager.registerStateCallback(req, sInstance.getMainThreadHandler()::post,
-                    new DownloadStateCallback() {
+
+            mDownloadManager.addStatusListener(req, sInstance.getMainThreadHandler()::post,
+                    new DownloadStatusListener() {
+                        @Override
+                        public void onStatusUpdated(DownloadRequest request, FileInfo fileInfo,
+                                @MbmsDownloadSession.DownloadStatus int state) {
+                            Toast.makeText(EmbmsTestDownloadApp.this,
+                                    "State Updated (" + fileInfo + ") state: " + state,
+                                    Toast.LENGTH_SHORT).show();
+                        }
+                    });
+
+            mDownloadManager.addProgressListener(req, sInstance.getMainThreadHandler()::post,
+                    new DownloadProgressListener() {
                         @Override
                         public void onProgressUpdated(DownloadRequest request, FileInfo fileInfo,
                                 int currentDownloadSize, int fullDownloadSize,
@@ -378,14 +370,6 @@
                                             + " fd: " + fullDownloadSize, Toast.LENGTH_SHORT)
                                     .show();
                         }
-
-                        @Override
-                        public void onStateUpdated(DownloadRequest request, FileInfo fileInfo,
-                                @MbmsDownloadSession.DownloadStatus int state) {
-                            Toast.makeText(EmbmsTestDownloadApp.this,
-                                    "State Updated (" + fileInfo + ") state: " + state,
-                                    Toast.LENGTH_SHORT).show();
-                        }
                     });
         });
     }
