• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2006 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.phone;
18 
19 import static android.provider.Telephony.Carriers.ENFORCE_MANAGED_URI;
20 
21 import android.app.ActionBar;
22 import android.app.Activity;
23 import android.app.DialogFragment;
24 import android.app.Fragment;
25 import android.app.FragmentManager;
26 import android.content.BroadcastReceiver;
27 import android.content.ContentResolver;
28 import android.content.Context;
29 import android.content.Intent;
30 import android.content.IntentFilter;
31 import android.content.pm.PackageManager;
32 import android.content.pm.ResolveInfo;
33 import android.database.ContentObserver;
34 import android.database.Cursor;
35 import android.net.Uri;
36 import android.os.AsyncTask;
37 import android.os.Bundle;
38 import android.os.Handler;
39 import android.os.Message;
40 import android.os.PersistableBundle;
41 import android.os.SystemProperties;
42 import android.os.UserHandle;
43 import android.os.UserManager;
44 import android.preference.ListPreference;
45 import android.preference.Preference;
46 import android.preference.PreferenceCategory;
47 import android.preference.PreferenceFragment;
48 import android.preference.PreferenceScreen;
49 import android.preference.SwitchPreference;
50 import android.provider.Settings;
51 import android.sysprop.SetupWizardProperties;
52 import android.telecom.PhoneAccountHandle;
53 import android.telecom.TelecomManager;
54 import android.telephony.CarrierConfigManager;
55 import android.telephony.PhoneStateListener;
56 import android.telephony.ServiceState;
57 import android.telephony.SubscriptionInfo;
58 import android.telephony.SubscriptionManager;
59 import android.telephony.TelephonyManager;
60 import android.telephony.euicc.EuiccManager;
61 import android.telephony.ims.ProvisioningManager;
62 import android.telephony.ims.feature.ImsFeature;
63 import android.text.TextUtils;
64 import android.util.Log;
65 import android.view.LayoutInflater;
66 import android.view.MenuItem;
67 import android.view.View;
68 import android.view.ViewGroup;
69 import android.widget.TabHost;
70 
71 import com.android.ims.ImsConfig;
72 import com.android.ims.ImsException;
73 import com.android.ims.ImsManager;
74 import com.android.internal.logging.MetricsLogger;
75 import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
76 import com.android.internal.telephony.Phone;
77 import com.android.internal.telephony.PhoneConstants;
78 import com.android.internal.telephony.TelephonyIntents;
79 import com.android.settingslib.RestrictedLockUtilsInternal;
80 
81 import java.util.ArrayList;
82 import java.util.Arrays;
83 import java.util.Iterator;
84 import java.util.List;
85 
86 /**
87  * "Mobile network settings" screen.  This screen lets you
88  * enable/disable mobile data, and control data roaming and other
89  * network-specific mobile data features.  It's used on non-voice-capable
90  * tablets as well as regular phone devices.
91  *
92  * Note that this Activity is part of the phone app, even though
93  * you reach it from the "Wireless & Networks" section of the main
94  * Settings app.  It's not part of the "Call settings" hierarchy that's
95  * available from the Phone app (see CallFeaturesSetting for that.)
96  */
97 
98 public class MobileNetworkSettings extends Activity  {
99 
100     // CID of the device.
101     private static final String KEY_CID = "ro.boot.cid";
102     // System Property which is used to decide whether the default eSIM UI will be shown,
103     // the default value is false.
104     private static final String KEY_ENABLE_ESIM_UI_BY_DEFAULT =
105             "esim.enable_esim_system_ui_by_default";
106 
107     private static final String LEGACY_ACTION_CONFIGURE_PHONE_ACCOUNT =
108             "android.telecom.action.CONNECTION_SERVICE_CONFIGURE";
109 
110     private enum TabState {
111         NO_TABS, UPDATE, DO_NOTHING
112     }
113 
114     @Override
onNewIntent(Intent intent)115     protected void onNewIntent(Intent intent) {
116         setIntent(intent);
117         MobileNetworkFragment fragment = (MobileNetworkFragment) getFragmentManager()
118                 .findFragmentById(R.id.network_setting_content);
119         if (fragment != null) {
120             fragment.onIntentUpdate(intent);
121         }
122     }
123 
124     @Override
onCreate(Bundle savedInstanceState)125     public void onCreate(Bundle savedInstanceState) {
126         super.onCreate(savedInstanceState);
127         setContentView(R.layout.network_setting);
128 
129         FragmentManager fragmentManager = getFragmentManager();
130         Fragment fragment = fragmentManager.findFragmentById(R.id.network_setting_content);
131         if (fragment == null) {
132             fragmentManager.beginTransaction()
133                     .add(R.id.network_setting_content, new MobileNetworkFragment())
134                     .commit();
135         }
136     }
137 
138     @Override
onOptionsItemSelected(final MenuItem item)139     public boolean onOptionsItemSelected(final MenuItem item) {
140         final int itemId = item.getItemId();
141         switch (itemId) {
142             // Respond to the action bar's Up/Home button
143             case android.R.id.home:
144                 finish();
145                 return true;
146         }
147         return super.onOptionsItemSelected(item);
148     }
149 
150 
151     /**
152      * Returns true if Wifi calling is enabled for at least one subscription.
153      */
isWifiCallingEnabled(Context context)154     public static boolean isWifiCallingEnabled(Context context) {
155         SubscriptionManager subManager = context.getSystemService(SubscriptionManager.class);
156         if (subManager == null) {
157             Log.e(MobileNetworkFragment.LOG_TAG,
158                     "isWifiCallingEnabled: couldn't get system service.");
159             return false;
160         }
161         for (int subId : subManager.getActiveSubscriptionIdList()) {
162             if (isWifiCallingEnabled(context, subId)) {
163                 return true;
164             }
165         }
166         return false;
167     }
168 
169     /**
170      * Returns true if Wifi calling is enabled for the specific subscription with id {@code subId}.
171      */
isWifiCallingEnabled(Context context, int subId)172     public static boolean isWifiCallingEnabled(Context context, int subId) {
173         final PhoneAccountHandle simCallManager =
174                 TelecomManager.from(context).getSimCallManagerForSubscription(subId);
175         final int phoneId = SubscriptionManager.getSlotIndex(subId);
176 
177         boolean isWifiCallingEnabled;
178         if (simCallManager != null) {
179             Intent intent = MobileNetworkSettings.buildPhoneAccountConfigureIntent(
180                     context, simCallManager);
181             PackageManager pm = context.getPackageManager();
182             isWifiCallingEnabled = intent != null
183                     && !pm.queryIntentActivities(intent, 0 /* flags */).isEmpty();
184         } else {
185             ImsManager imsMgr = ImsManager.getInstance(context, phoneId);
186             isWifiCallingEnabled = imsMgr != null
187                     && imsMgr.isWfcEnabledByPlatform()
188                     && imsMgr.isWfcProvisionedOnDevice()
189                     && isImsServiceStateReady(imsMgr);
190         }
191 
192         return isWifiCallingEnabled;
193     }
194 
195     /**
196      * Whether to show the entry point to eUICC settings.
197      *
198      * <p>We show the entry point on any device which supports eUICC as long as either the eUICC
199      * was ever provisioned (that is, at least one profile was ever downloaded onto it), or if
200      * the user has enabled development mode.
201      */
showEuiccSettings(Context context)202     public static boolean showEuiccSettings(Context context) {
203         EuiccManager euiccManager =
204                 (EuiccManager) context.getSystemService(Context.EUICC_SERVICE);
205         if (!euiccManager.isEnabled()) {
206             return false;
207         }
208 
209         ContentResolver cr = context.getContentResolver();
210 
211         TelephonyManager tm =
212                 (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
213         String currentCountry = tm.getNetworkCountryIso().toLowerCase();
214         String supportedCountries =
215                 Settings.Global.getString(cr, Settings.Global.EUICC_SUPPORTED_COUNTRIES);
216         boolean inEsimSupportedCountries = false;
217         if (TextUtils.isEmpty(currentCountry)) {
218             inEsimSupportedCountries = true;
219         } else if (!TextUtils.isEmpty(supportedCountries)) {
220             List<String> supportedCountryList =
221                     Arrays.asList(TextUtils.split(supportedCountries.toLowerCase(), ","));
222             if (supportedCountryList.contains(currentCountry)) {
223                 inEsimSupportedCountries = true;
224             }
225         }
226         final boolean esimIgnoredDevice =
227                 SetupWizardProperties.esim_cid_ignore()
228                         .contains(SystemProperties.get(KEY_CID, null));
229         final boolean enabledEsimUiByDefault =
230                 SystemProperties.getBoolean(KEY_ENABLE_ESIM_UI_BY_DEFAULT, true);
231         final boolean euiccProvisioned =
232                 Settings.Global.getInt(cr, Settings.Global.EUICC_PROVISIONED, 0) != 0;
233         final boolean inDeveloperMode =
234                 Settings.Global.getInt(cr, Settings.Global.DEVELOPMENT_SETTINGS_ENABLED, 0) != 0;
235 
236         return (inDeveloperMode || euiccProvisioned
237                 || (!esimIgnoredDevice && enabledEsimUiByDefault && inEsimSupportedCountries));
238     }
239 
240     /**
241      * Whether to show the Enhanced 4G LTE settings in search result.
242      *
243      * <p>We show this settings if the VoLTE can be enabled by this device and the carrier app
244      * doesn't set {@link CarrierConfigManager#KEY_HIDE_ENHANCED_4G_LTE_BOOL} to false.
245      */
hideEnhanced4gLteSettings(Context context)246     public static boolean hideEnhanced4gLteSettings(Context context) {
247         final CarrierConfigManager carrierConfigManager = new CarrierConfigManager(context);
248         final List<SubscriptionInfo> sil =
249                 SubscriptionManager.from(context).getActiveSubscriptionInfoList();
250         // Check all active subscriptions. We only hide the button if it's disabled for all
251         // active subscriptions.
252         if (sil != null) {
253             for (SubscriptionInfo subInfo : sil) {
254                 int phoneId = SubscriptionManager.getPhoneId(subInfo.getSubscriptionId());
255                 ImsManager imsManager = ImsManager.getInstance(context, phoneId);
256                 PersistableBundle carrierConfig = carrierConfigManager.getConfigForSubId(
257                         subInfo.getSubscriptionId());
258                 if ((imsManager.isVolteEnabledByPlatform()
259                         && imsManager.isVolteProvisionedOnDevice())
260                         || carrierConfig.getBoolean(
261                         CarrierConfigManager.KEY_HIDE_ENHANCED_4G_LTE_BOOL)) {
262                     return false;
263                 }
264             }
265         }
266 
267         return true;
268     }
269 
270     /**
271      * Returns if DPC APNs are enforced.
272      */
isDpcApnEnforced(Context context)273     public static boolean isDpcApnEnforced(Context context) {
274         try (Cursor enforceCursor = context.getContentResolver().query(ENFORCE_MANAGED_URI,
275                 null, null, null, null)) {
276             if (enforceCursor == null || enforceCursor.getCount() != 1) {
277                 return false;
278             }
279             enforceCursor.moveToFirst();
280             return enforceCursor.getInt(0) > 0;
281         }
282     }
283 
isImsServiceStateReady(ImsManager imsMgr)284     private static boolean isImsServiceStateReady(ImsManager imsMgr) {
285         boolean isImsServiceStateReady = false;
286 
287         try {
288             if (imsMgr != null && imsMgr.getImsServiceState() == ImsFeature.STATE_READY) {
289                 isImsServiceStateReady = true;
290             }
291         } catch (ImsException ex) {
292             Log.e(MobileNetworkFragment.LOG_TAG,
293                     "Exception when trying to get ImsServiceStatus: " + ex);
294         }
295 
296         Log.d(MobileNetworkFragment.LOG_TAG, "isImsServiceStateReady=" + isImsServiceStateReady);
297         return isImsServiceStateReady;
298     }
299 
300 
buildPhoneAccountConfigureIntent( Context context, PhoneAccountHandle accountHandle)301     private static Intent buildPhoneAccountConfigureIntent(
302             Context context, PhoneAccountHandle accountHandle) {
303         Intent intent = buildConfigureIntent(
304                 context, accountHandle, TelecomManager.ACTION_CONFIGURE_PHONE_ACCOUNT);
305 
306         if (intent == null) {
307             // If the new configuration didn't work, try the old configuration intent.
308             intent = buildConfigureIntent(
309                     context, accountHandle, LEGACY_ACTION_CONFIGURE_PHONE_ACCOUNT);
310             if (intent != null) {
311                 Log.w(MobileNetworkFragment.LOG_TAG,
312                         "Phone account using old configuration intent: " + accountHandle);
313             }
314         }
315         return intent;
316     }
317 
buildConfigureIntent( Context context, PhoneAccountHandle accountHandle, String actionStr)318     private static Intent buildConfigureIntent(
319             Context context, PhoneAccountHandle accountHandle, String actionStr) {
320         if (accountHandle == null || accountHandle.getComponentName() == null
321                 || TextUtils.isEmpty(accountHandle.getComponentName().getPackageName())) {
322             return null;
323         }
324 
325         // Build the settings intent.
326         Intent intent = new Intent(actionStr);
327         intent.setPackage(accountHandle.getComponentName().getPackageName());
328         intent.addCategory(Intent.CATEGORY_DEFAULT);
329         intent.putExtra(TelecomManager.EXTRA_PHONE_ACCOUNT_HANDLE, accountHandle);
330 
331         // Check to see that the phone account package can handle the setting intent.
332         PackageManager pm = context.getPackageManager();
333         List<ResolveInfo> resolutions = pm.queryIntentActivities(intent, 0);
334         if (resolutions.size() == 0) {
335             intent = null;  // set no intent if the package cannot handle it.
336         }
337 
338         return intent;
339     }
340 
341     public static class MobileNetworkFragment extends PreferenceFragment implements
342             Preference.OnPreferenceChangeListener, RoamingDialogFragment.RoamingDialogListener {
343 
344         // debug data
345         private static final String LOG_TAG = "NetworkSettings";
346         private static final boolean DBG = true;
347         public static final int REQUEST_CODE_EXIT_ECM = 17;
348 
349         // Number of active Subscriptions to show tabs
350         private static final int TAB_THRESHOLD = 2;
351 
352         // Number of last phone number digits shown in Euicc Setting tab
353         private static final int NUM_LAST_PHONE_DIGITS = 4;
354 
355         // fragment tag for roaming data dialog
356         private static final String ROAMING_TAG = "RoamingDialogFragment";
357 
358         //String keys for preference lookup
359         private static final String BUTTON_PREFERED_NETWORK_MODE = "preferred_network_mode_key";
360         private static final String BUTTON_ROAMING_KEY = "button_roaming_key";
361         private static final String BUTTON_CDMA_LTE_DATA_SERVICE_KEY = "cdma_lte_data_service_key";
362         private static final String BUTTON_ENABLED_NETWORKS_KEY = "enabled_networks_key";
363         private static final String BUTTON_4G_LTE_KEY = "enhanced_4g_lte";
364         private static final String BUTTON_CELL_BROADCAST_SETTINGS = "cell_broadcast_settings";
365         private static final String BUTTON_CARRIER_SETTINGS_KEY = "carrier_settings_key";
366         private static final String BUTTON_CDMA_SYSTEM_SELECT_KEY = "cdma_system_select_key";
367         private static final String BUTTON_CDMA_SUBSCRIPTION_KEY = "cdma_subscription_key";
368         private static final String BUTTON_CARRIER_SETTINGS_EUICC_KEY =
369                 "carrier_settings_euicc_key";
370         private static final String BUTTON_WIFI_CALLING_KEY = "wifi_calling_key";
371         private static final String BUTTON_VIDEO_CALLING_KEY = "video_calling_key";
372         private static final String BUTTON_MOBILE_DATA_ENABLE_KEY = "mobile_data_enable";
373         private static final String BUTTON_DATA_USAGE_KEY = "data_usage_summary";
374         private static final String BUTTON_ADVANCED_OPTIONS_KEY = "advanced_options";
375         private static final String CATEGORY_CALLING_KEY = "calling";
376         private static final String CATEGORY_GSM_APN_EXPAND_KEY = "category_gsm_apn_key";
377         private static final String CATEGORY_CDMA_APN_EXPAND_KEY = "category_cdma_apn_key";
378         private static final String BUTTON_GSM_APN_EXPAND_KEY = "button_gsm_apn_key";
379         private static final String BUTTON_CDMA_APN_EXPAND_KEY = "button_cdma_apn_key";
380 
381         private final BroadcastReceiver mPhoneChangeReceiver = new PhoneChangeReceiver();
382         private final ContentObserver mDpcEnforcedContentObserver = new DpcApnEnforcedObserver();
383 
384         static final int preferredNetworkMode = Phone.PREFERRED_NT_MODE;
385 
386         //Information about logical "up" Activity
387         private static final String UP_ACTIVITY_PACKAGE = "com.android.settings";
388         private static final String UP_ACTIVITY_CLASS =
389                 "com.android.settings.Settings$WirelessSettingsActivity";
390 
391         //Information that needs to save into Bundle.
392         private static final String EXPAND_ADVANCED_FIELDS = "expand_advanced_fields";
393         //Intent extra to indicate expand all fields.
394         private static final String EXPAND_EXTRA = "expandable";
395 
396         private SubscriptionManager mSubscriptionManager;
397         private TelephonyManager mTelephonyManager;
398         private CarrierConfigManager mCarrierConfigManager;
399         private int mSubId;
400 
401         //UI objects
402         private AdvancedOptionsPreference mAdvancedOptions;
403         private ListPreference mButtonPreferredNetworkMode;
404         private ListPreference mButtonEnabledNetworks;
405         private RestrictedSwitchPreference mButtonDataRoam;
406         private SwitchPreference mButton4glte;
407         private Preference mLteDataServicePref;
408         private Preference mEuiccSettingsPref;
409         private PreferenceCategory mCallingCategory;
410         private Preference mWiFiCallingPref;
411         private SwitchPreference mVideoCallingPref;
412         private NetworkSelectListPreference mButtonNetworkSelect;
413         private MobileDataPreference mMobileDataPref;
414         private DataUsagePreference mDataUsagePref;
415 
416         private static final String iface = "rmnet0"; //TODO: this will go away
417         private List<SubscriptionInfo> mActiveSubInfos;
418 
419         private UserManager mUm;
420         private ImsManager mImsMgr;
421         private MyHandler mHandler;
422         private boolean mOkClicked;
423         private boolean mExpandAdvancedFields;
424 
425         // We assume the the value returned by mTabHost.getCurrentTab() == slotId
426         private TabHost mTabHost;
427 
428         //GsmUmts options and Cdma options
429         GsmUmtsOptions mGsmUmtsOptions;
430         CdmaOptions mCdmaOptions;
431 
432         private Preference mClickedPreference;
433         private boolean mShow4GForLTE = false;
434         private boolean mIsGlobalCdma;
435         private boolean mOnlyAutoSelectInHomeNW;
436         private boolean mUnavailable;
437 
438         private class PhoneCallStateListener extends PhoneStateListener {
439             /*
440              * Enable/disable the 'Enhanced 4G LTE Mode' when in/out of a call
441              * and depending on TTY mode and TTY support over VoLTE.
442              * @see android.telephony.PhoneStateListener#onCallStateChanged(int,
443              * java.lang.String)
444              */
445             @Override
onCallStateChanged(int state, String incomingNumber)446             public void onCallStateChanged(int state, String incomingNumber) {
447                 if (DBG) log("PhoneStateListener.onCallStateChanged: state=" + state);
448 
449                 updateEnhanced4gLteState();
450                 updateWiFiCallState();
451                 updateVideoCallState();
452                 updatePreferredNetworkType();
453             }
454 
455             /**
456              * Listen to different subId if it's changed.
457              */
updateSubscriptionId(Integer subId)458             protected void updateSubscriptionId(Integer subId) {
459                 if (subId.equals(PhoneCallStateListener.this.mSubId)) {
460                     return;
461                 }
462 
463                 mTelephonyManager.listen(this, PhoneStateListener.LISTEN_NONE);
464 
465                 // Now, listen to new subId if it's valid. register the listener with
466                 // mTelephonyManager instance created for the new subId.
467                 if (SubscriptionManager.isValidSubscriptionId(subId)) {
468                     mTelephonyManager.listen(this, PhoneStateListener.LISTEN_CALL_STATE);
469                 }
470             }
471         }
472 
473         private final PhoneCallStateListener mPhoneStateListener = new PhoneCallStateListener();
474 
475         @Override
onPositiveButtonClick(DialogFragment dialog)476         public void onPositiveButtonClick(DialogFragment dialog) {
477             mTelephonyManager.setDataRoamingEnabled(true);
478             mButtonDataRoam.setChecked(true);
479             MetricsLogger.action(getContext(),
480                     getMetricsEventCategory(getPreferenceScreen(), mButtonDataRoam),
481                     true);
482         }
483 
484         @Override
onViewCreated(View view, Bundle savedInstanceState)485         public void onViewCreated(View view, Bundle savedInstanceState) {
486             if (getListView() != null) {
487                 getListView().setDivider(null);
488             }
489         }
490 
onIntentUpdate(Intent intent)491         public void onIntentUpdate(Intent intent) {
492             if (!mUnavailable) {
493                 updateCurrentTab(intent.getExtras());
494             }
495         }
496 
497         /**
498          * Invoked on each preference click in this hierarchy, overrides
499          * PreferenceActivity's implementation.  Used to make sure we track the
500          * preference click events.
501          */
502         @Override
onPreferenceTreeClick(PreferenceScreen preferenceScreen, Preference preference)503         public boolean onPreferenceTreeClick(PreferenceScreen preferenceScreen,
504                                              Preference preference) {
505             sendMetricsEventPreferenceClicked(preferenceScreen, preference);
506 
507             /** TODO: Refactor and get rid of the if's using subclasses */
508             if (preference.getKey().equals(BUTTON_4G_LTE_KEY)) {
509                 return true;
510             } else if (mGsmUmtsOptions != null &&
511                     mGsmUmtsOptions.preferenceTreeClick(preference) == true) {
512                 return true;
513             } else if (mCdmaOptions != null &&
514                     mCdmaOptions.preferenceTreeClick(preference) == true) {
515                 if (mTelephonyManager.getEmergencyCallbackMode()) {
516 
517                     mClickedPreference = preference;
518 
519                     // In ECM mode launch ECM app dialog
520                     startActivityForResult(
521                             new Intent(TelephonyIntents.ACTION_SHOW_NOTICE_ECM_BLOCK_OTHERS, null),
522                             REQUEST_CODE_EXIT_ECM);
523                 }
524                 return true;
525             } else if (preference == mButtonPreferredNetworkMode) {
526                 //displays the value taken from the Settings.System
527                 int settingsNetworkMode = android.provider.Settings.Global.getInt(
528                         getContext().getContentResolver(),
529                         android.provider.Settings.Global.PREFERRED_NETWORK_MODE + mSubId,
530                         preferredNetworkMode);
531                 mButtonPreferredNetworkMode.setValue(Integer.toString(settingsNetworkMode));
532                 return true;
533             } else if (preference == mLteDataServicePref) {
534                 String tmpl = android.provider.Settings.Global.getString(
535                         getActivity().getContentResolver(),
536                         android.provider.Settings.Global.SETUP_PREPAID_DATA_SERVICE_URL);
537                 if (!TextUtils.isEmpty(tmpl)) {
538                     String imsi = mTelephonyManager.getSubscriberId();
539                     if (imsi == null) {
540                         imsi = "";
541                     }
542                     final String url = TextUtils.isEmpty(tmpl) ? null
543                             : TextUtils.expandTemplate(tmpl, imsi).toString();
544                     Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
545                     startActivity(intent);
546                 } else {
547                     android.util.Log.e(LOG_TAG, "Missing SETUP_PREPAID_DATA_SERVICE_URL");
548                 }
549                 return true;
550             }  else if (preference == mButtonEnabledNetworks) {
551                 int settingsNetworkMode = android.provider.Settings.Global.getInt(
552                         getContext().getContentResolver(),
553                         android.provider.Settings.Global.PREFERRED_NETWORK_MODE + mSubId,
554                         preferredNetworkMode);
555                 mButtonEnabledNetworks.setValue(Integer.toString(settingsNetworkMode));
556                 return true;
557             } else if (preference == mButtonDataRoam) {
558                 // Do not disable the preference screen if the user clicks Data roaming.
559                 return true;
560             } else if (preference == mEuiccSettingsPref) {
561                 Intent intent = new Intent(EuiccManager.ACTION_MANAGE_EMBEDDED_SUBSCRIPTIONS);
562                 startActivity(intent);
563                 return true;
564             } else if (preference == mWiFiCallingPref || preference == mVideoCallingPref
565                     || preference == mMobileDataPref || preference == mDataUsagePref) {
566                 return false;
567             } else if (preference == mAdvancedOptions) {
568                 mExpandAdvancedFields = true;
569                 updateBody();
570                 return true;
571             } else {
572                 // if the button is anything but the simple toggle preference,
573                 // we'll need to disable all preferences to reject all click
574                 // events until the sub-activity's UI comes up.
575                 preferenceScreen.setEnabled(false);
576                 // Let the intents be launched by the Preference manager
577                 return false;
578             }
579         }
580 
581         private final SubscriptionManager.OnSubscriptionsChangedListener
582                 mOnSubscriptionsChangeListener
583                 = new SubscriptionManager.OnSubscriptionsChangedListener() {
584             @Override
585             public void onSubscriptionsChanged() {
586                 if (DBG) log("onSubscriptionsChanged:");
587                 initializeSubscriptions();
588             }
589         };
590 
getSlotIdFromBundle(Bundle data)591         private int getSlotIdFromBundle(Bundle data) {
592             int subId = -1;
593             if (data != null) {
594                 subId = data.getInt(Settings.EXTRA_SUB_ID, -1);
595             }
596             return SubscriptionManager.getSlotIndex(subId);
597         }
598 
initializeSubscriptions()599         private void initializeSubscriptions() {
600             final Activity activity = getActivity();
601             if (activity == null || activity.isDestroyed()) {
602                 // Process preferences in activity only if its not destroyed
603                 return;
604             }
605             int currentTab = 0;
606             if (DBG) log("initializeSubscriptions:+");
607 
608             // Before updating the the active subscription list check
609             // if tab updating is needed as the list is changing.
610             List<SubscriptionInfo> sil = mSubscriptionManager.getActiveSubscriptionInfoList();
611             MobileNetworkSettings.TabState state = isUpdateTabsNeeded(sil);
612 
613             // Update to the active subscription list
614             mActiveSubInfos.clear();
615             if (sil != null) {
616                 mActiveSubInfos.addAll(sil);
617                 // If there is only 1 sim then currenTab should represent slot no. of the sim.
618                 if (sil.size() == 1) {
619                     currentTab = sil.get(0).getSimSlotIndex();
620                 }
621             }
622 
623             switch (state) {
624                 case UPDATE: {
625                     if (DBG) log("initializeSubscriptions: UPDATE");
626                     currentTab = mTabHost != null ? mTabHost.getCurrentTab() : 0;
627 
628                     mTabHost = (TabHost) getActivity().findViewById(android.R.id.tabhost);
629                     mTabHost.setup();
630 
631                     // Update the tabName. Since the mActiveSubInfos are in slot order
632                     // we can iterate though the tabs and subscription info in one loop. But
633                     // we need to handle the case where a slot may be empty.
634 
635                     Iterator<SubscriptionInfo> siIterator = mActiveSubInfos.listIterator();
636                     SubscriptionInfo si = siIterator.hasNext() ? siIterator.next() : null;
637                     for (int simSlotIndex = 0; simSlotIndex  < mActiveSubInfos.size();
638                          simSlotIndex++) {
639                         String tabName;
640                         if (si != null && si.getSimSlotIndex() == simSlotIndex) {
641                             // Slot is not empty and we match
642                             tabName = String.valueOf(si.getDisplayName());
643                             si = siIterator.hasNext() ? siIterator.next() : null;
644                         } else {
645                             // Slot is empty, set name to unknown
646                             tabName = getResources().getString(R.string.unknown);
647                         }
648                         if (DBG) {
649                             log("initializeSubscriptions:tab=" + simSlotIndex + " name=" + tabName);
650                         }
651 
652                         mTabHost.addTab(buildTabSpec(String.valueOf(simSlotIndex), tabName));
653                     }
654 
655                     mTabHost.setOnTabChangedListener(mTabListener);
656                     mTabHost.setCurrentTab(currentTab);
657                     break;
658                 }
659                 case NO_TABS: {
660                     if (DBG) log("initializeSubscriptions: NO_TABS");
661 
662                     if (mTabHost != null) {
663                         mTabHost.clearAllTabs();
664                         mTabHost = null;
665                     }
666                     break;
667                 }
668                 case DO_NOTHING: {
669                     if (DBG) log("initializeSubscriptions: DO_NOTHING");
670                     if (mTabHost != null) {
671                         currentTab = mTabHost.getCurrentTab();
672                     }
673                     break;
674                 }
675             }
676             updatePhone(currentTab);
677             updateBody();
678             if (DBG) log("initializeSubscriptions:-");
679         }
680 
isUpdateTabsNeeded(List<SubscriptionInfo> newSil)681         private MobileNetworkSettings.TabState isUpdateTabsNeeded(List<SubscriptionInfo> newSil) {
682             TabState state = MobileNetworkSettings.TabState.DO_NOTHING;
683             if (newSil == null) {
684                 if (mActiveSubInfos.size() >= TAB_THRESHOLD) {
685                     if (DBG) log("isUpdateTabsNeeded: NO_TABS, size unknown and was tabbed");
686                     state = MobileNetworkSettings.TabState.NO_TABS;
687                 }
688             } else if (newSil.size() < TAB_THRESHOLD && mActiveSubInfos.size() >= TAB_THRESHOLD) {
689                 if (DBG) log("isUpdateTabsNeeded: NO_TABS, size went to small");
690                 state = MobileNetworkSettings.TabState.NO_TABS;
691             } else if (newSil.size() >= TAB_THRESHOLD && mActiveSubInfos.size() < TAB_THRESHOLD) {
692                 if (DBG) log("isUpdateTabsNeeded: UPDATE, size changed");
693                 state = MobileNetworkSettings.TabState.UPDATE;
694             } else if (newSil.size() >= TAB_THRESHOLD) {
695                 Iterator<SubscriptionInfo> siIterator = mActiveSubInfos.iterator();
696                 for(SubscriptionInfo newSi : newSil) {
697                     SubscriptionInfo curSi = siIterator.next();
698                     if (!newSi.getDisplayName().equals(curSi.getDisplayName())) {
699                         if (DBG) log("isUpdateTabsNeeded: UPDATE, new name="
700                                 + newSi.getDisplayName());
701                         state = MobileNetworkSettings.TabState.UPDATE;
702                         break;
703                     }
704                 }
705             }
706             if (DBG) {
707                 Log.i(LOG_TAG, "isUpdateTabsNeeded:- " + state
708                         + " newSil.size()=" + ((newSil != null) ? newSil.size() : 0)
709                         + " mActiveSubInfos.size()=" + mActiveSubInfos.size());
710             }
711             return state;
712         }
713 
714         private TabHost.OnTabChangeListener mTabListener = new TabHost.OnTabChangeListener() {
715             @Override
716             public void onTabChanged(String tabId) {
717                 if (DBG) log("onTabChanged:");
718                 // The User has changed tab; update the body.
719                 updatePhone(Integer.parseInt(tabId));
720                 updateBody();
721             }
722         };
723 
updatePhone(int slotId)724         private void updatePhone(int slotId) {
725             final SubscriptionInfo sir = mSubscriptionManager
726                     .getActiveSubscriptionInfoForSimSlotIndex(slotId);
727 
728             if (sir != null) {
729                 mSubId = sir.getSubscriptionId();
730 
731                 Log.i(LOG_TAG, "updatePhone:- slotId=" + slotId + " sir=" + sir);
732 
733                 mImsMgr = ImsManager.getInstance(getContext(),
734                         SubscriptionManager.getPhoneId(mSubId));
735                 mTelephonyManager = new TelephonyManager(getContext(), mSubId);
736                 if (mImsMgr == null) {
737                     log("updatePhone :: Could not get ImsManager instance!");
738                 } else if (DBG) {
739                     log("updatePhone :: mImsMgr=" + mImsMgr);
740                 }
741             } else {
742                 // There is no active subscription in the given slot.
743                 mSubId = SubscriptionManager.INVALID_SUBSCRIPTION_ID;
744             }
745 
746             mPhoneStateListener.updateSubscriptionId(mSubId);
747         }
748 
749         private TabHost.TabContentFactory mEmptyTabContent = new TabHost.TabContentFactory() {
750             @Override
751             public View createTabContent(String tag) {
752                 return new View(mTabHost.getContext());
753             }
754         };
755 
buildTabSpec(String tag, String title)756         private TabHost.TabSpec buildTabSpec(String tag, String title) {
757             return mTabHost.newTabSpec(tag).setIndicator(title).setContent(
758                     mEmptyTabContent);
759         }
760 
updateCurrentTab(Bundle data)761         private void updateCurrentTab(Bundle data) {
762             int slotId = getSlotIdFromBundle(data);
763             if (slotId >= 0 && mTabHost != null && mTabHost.getCurrentTab() != slotId) {
764                 mTabHost.setCurrentTab(slotId);
765             }
766         }
767 
768         @Override
onSaveInstanceState(Bundle outState)769         public void onSaveInstanceState(Bundle outState) {
770             super.onSaveInstanceState(outState);
771 
772             // If advanced fields are already expanded, we save it and expand it
773             // when it's re-created.
774             outState.putBoolean(EXPAND_ADVANCED_FIELDS, mExpandAdvancedFields);
775 
776             // Save subId of currently shown tab.
777             outState.putInt(Settings.EXTRA_SUB_ID, mSubId);
778         }
779 
780         @Override
onCreate(Bundle icicle)781         public void onCreate(Bundle icicle) {
782             Log.i(LOG_TAG, "onCreate:+");
783             super.onCreate(icicle);
784 
785             final Activity activity = getActivity();
786             if (activity == null || activity.isDestroyed()) {
787                 Log.e(LOG_TAG, "onCreate:- with no valid activity.");
788                 return;
789             }
790 
791             mHandler = new MyHandler();
792             mUm = (UserManager) activity.getSystemService(Context.USER_SERVICE);
793             mSubscriptionManager = SubscriptionManager.from(activity);
794             mTelephonyManager = (TelephonyManager) activity.getSystemService(
795                             Context.TELEPHONY_SERVICE);
796             mCarrierConfigManager = new CarrierConfigManager(getContext());
797 
798             if (icicle != null) {
799                 mExpandAdvancedFields = icicle.getBoolean(EXPAND_ADVANCED_FIELDS, false);
800             } else if (getActivity().getIntent().getBooleanExtra(EXPAND_EXTRA, false)) {
801                 mExpandAdvancedFields = true;
802             }
803 
804             addPreferencesFromResource(R.xml.network_setting_fragment);
805 
806             mButton4glte = (SwitchPreference)findPreference(BUTTON_4G_LTE_KEY);
807             mButton4glte.setOnPreferenceChangeListener(this);
808 
809             mCallingCategory = (PreferenceCategory) findPreference(CATEGORY_CALLING_KEY);
810             mWiFiCallingPref = findPreference(BUTTON_WIFI_CALLING_KEY);
811             mVideoCallingPref = (SwitchPreference) findPreference(BUTTON_VIDEO_CALLING_KEY);
812             mMobileDataPref = (MobileDataPreference) findPreference(BUTTON_MOBILE_DATA_ENABLE_KEY);
813             mDataUsagePref = (DataUsagePreference) findPreference(BUTTON_DATA_USAGE_KEY);
814 
815             //get UI object references
816             PreferenceScreen prefSet = getPreferenceScreen();
817 
818             mButtonDataRoam = (RestrictedSwitchPreference) prefSet.findPreference(
819                     BUTTON_ROAMING_KEY);
820             mButtonPreferredNetworkMode = (ListPreference) prefSet.findPreference(
821                     BUTTON_PREFERED_NETWORK_MODE);
822             mButtonEnabledNetworks = (ListPreference) prefSet.findPreference(
823                     BUTTON_ENABLED_NETWORKS_KEY);
824             mAdvancedOptions = (AdvancedOptionsPreference) prefSet.findPreference(
825                     BUTTON_ADVANCED_OPTIONS_KEY);
826             mButtonDataRoam.setOnPreferenceChangeListener(this);
827 
828             mLteDataServicePref = prefSet.findPreference(BUTTON_CDMA_LTE_DATA_SERVICE_KEY);
829 
830             mEuiccSettingsPref = prefSet.findPreference(BUTTON_CARRIER_SETTINGS_EUICC_KEY);
831             mEuiccSettingsPref.setOnPreferenceChangeListener(this);
832 
833             // Initialize mActiveSubInfo
834             int max = mSubscriptionManager.getActiveSubscriptionInfoCountMax();
835             mActiveSubInfos = new ArrayList<SubscriptionInfo>(max);
836 
837             int currentTab = mTabHost != null ? mTabHost.getCurrentTab() : 0;
838             updatePhone(currentTab);
839             if (hasActiveSubscriptions()) {
840                 updateEnabledNetworksEntries();
841             }
842             Log.i(LOG_TAG, "onCreate:-");
843         }
844 
845         @Override
onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)846         public View onCreateView(LayoutInflater inflater, ViewGroup container,
847                 Bundle savedInstanceState) {
848             return inflater.inflate(com.android.internal.R.layout.common_tab_settings,
849                     container, false);
850         }
851 
852         @Override
onActivityCreated(Bundle savedInstanceState)853         public void onActivityCreated(Bundle savedInstanceState) {
854             super.onActivityCreated(savedInstanceState);
855             if (mUm.hasUserRestriction(UserManager.DISALLOW_CONFIG_MOBILE_NETWORKS)
856                     || !mUm.isSystemUser()) {
857                 mUnavailable = true;
858                 getActivity().setContentView(R.layout.telephony_disallowed_preference_screen);
859             } else {
860                 initializeSubscriptions();
861 
862                 if (savedInstanceState != null) {
863                     updateCurrentTab(savedInstanceState);
864                 } else {
865                     updateCurrentTab(getActivity().getIntent().getExtras());
866                 }
867             }
868         }
869 
870         private class PhoneChangeReceiver extends BroadcastReceiver {
871             @Override
onReceive(Context context, Intent intent)872             public void onReceive(Context context, Intent intent) {
873                 Log.i(LOG_TAG, "onReceive:");
874                 if (getActivity() == null || getContext() == null) {
875                     // Received broadcast and activity is in the process of being torn down.
876                     return;
877                 }
878                 // When the radio changes (ex: CDMA->GSM), refresh all options.
879                 updateBody();
880             }
881         }
882 
883         private class DpcApnEnforcedObserver extends ContentObserver {
DpcApnEnforcedObserver()884             DpcApnEnforcedObserver() {
885                 super(null);
886             }
887 
888             @Override
onChange(boolean selfChange)889             public void onChange(boolean selfChange) {
890                 Log.i(LOG_TAG, "DPC enforced onChange:");
891                 if (getActivity() == null || getContext() == null) {
892                     // Received content change and activity is in the process of being torn down.
893                     return;
894                 }
895                 updateBody();
896             }
897         }
898 
899         private final ProvisioningManager.Callback mProvisioningCallback =
900                 new ProvisioningManager.Callback() {
901             @Override
902             public void onProvisioningIntChanged(int item, int value) {
903                 if (item == ImsConfig.ConfigConstants.VOICE_OVER_WIFI_SETTING_ENABLED
904                         || item == ImsConfig.ConfigConstants.VLT_SETTING_ENABLED
905                         || item == ImsConfig.ConfigConstants.LVC_SETTING_ENABLED) {
906                     updateBody();
907                 }
908             }
909         };
910 
911         @Override
onDestroy()912         public void onDestroy() {
913             super.onDestroy();
914             if (mMobileDataPref != null) {
915                 mMobileDataPref.dispose();
916             }
917         }
918 
919         @Override
onResume()920         public void onResume() {
921             super.onResume();
922             Log.i(LOG_TAG, "onResume:+");
923 
924             if (mUnavailable) {
925                 Log.i(LOG_TAG, "onResume:- ignore mUnavailable == false");
926                 return;
927             }
928 
929             // upon resumption from the sub-activity, make sure we re-enable the
930             // preferences.
931             getPreferenceScreen().setEnabled(true);
932 
933             // Set UI state in onResume because a user could go home, launch some
934             // app to change this setting's backend, and re-launch this settings app
935             // and the UI state would be inconsistent with actual state
936             mButtonDataRoam.setChecked(mTelephonyManager.isDataRoamingEnabled());
937 
938             if (getPreferenceScreen().findPreference(BUTTON_PREFERED_NETWORK_MODE) != null
939                     || getPreferenceScreen().findPreference(BUTTON_ENABLED_NETWORKS_KEY) != null)  {
940                 updatePreferredNetworkUIFromDb();
941             }
942 
943             mTelephonyManager.createForSubscriptionId(mSubId)
944                     .listen(mPhoneStateListener, PhoneStateListener.LISTEN_CALL_STATE);
945 
946             // NOTE: Buttons will be enabled/disabled in mPhoneStateListener
947             updateEnhanced4gLteState();
948 
949             // Video calling and WiFi calling state might have changed.
950             updateCallingCategory();
951 
952             mSubscriptionManager.addOnSubscriptionsChangedListener(mOnSubscriptionsChangeListener);
953 
954             final Context context = getActivity();
955             IntentFilter intentFilter = new IntentFilter(
956                     TelephonyIntents.ACTION_RADIO_TECHNOLOGY_CHANGED);
957             context.registerReceiver(mPhoneChangeReceiver, intentFilter);
958             context.getContentResolver().registerContentObserver(ENFORCE_MANAGED_URI, false,
959                     mDpcEnforcedContentObserver);
960 
961             // Register callback for provisioning changes.
962             try {
963                 if (mImsMgr != null) {
964                     mImsMgr.getConfigInterface().addConfigCallback(mProvisioningCallback);
965                 }
966             } catch (ImsException e) {
967                 Log.w(LOG_TAG, "onResume: Unable to register callback for provisioning changes.");
968             }
969 
970             Log.i(LOG_TAG, "onResume:-");
971 
972         }
973 
hasActiveSubscriptions()974         private boolean hasActiveSubscriptions() {
975             return mActiveSubInfos.size() > 0;
976         }
977 
updateBodyBasicFields(Activity activity, PreferenceScreen prefSet, int phoneSubId, boolean hasActiveSubscriptions)978         private void updateBodyBasicFields(Activity activity, PreferenceScreen prefSet,
979                 int phoneSubId, boolean hasActiveSubscriptions) {
980             Context context = activity.getApplicationContext();
981 
982             ActionBar actionBar = activity.getActionBar();
983             if (actionBar != null) {
984                 // android.R.id.home will be triggered in onOptionsItemSelected()
985                 actionBar.setDisplayHomeAsUpEnabled(true);
986             }
987 
988             prefSet.addPreference(mMobileDataPref);
989             prefSet.addPreference(mButtonDataRoam);
990             prefSet.addPreference(mDataUsagePref);
991 
992             mMobileDataPref.setEnabled(hasActiveSubscriptions);
993             mButtonDataRoam.setEnabled(hasActiveSubscriptions);
994             mDataUsagePref.setEnabled(hasActiveSubscriptions);
995 
996             if (hasActiveSubscriptions) {
997                 // Customized preferences needs to be initialized with subId.
998                 mMobileDataPref.initialize(phoneSubId);
999                 mDataUsagePref.initialize(phoneSubId);
1000 
1001                 // Initialize states of mButtonDataRoam.
1002                 mButtonDataRoam.setChecked(mTelephonyManager.isDataRoamingEnabled());
1003                 mButtonDataRoam.setDisabledByAdmin(false);
1004                 if (mButtonDataRoam.isEnabled()) {
1005                     if (RestrictedLockUtilsInternal.hasBaseUserRestriction(context,
1006                             UserManager.DISALLOW_DATA_ROAMING, UserHandle.myUserId())) {
1007                         mButtonDataRoam.setEnabled(false);
1008                     } else {
1009                         mButtonDataRoam.checkRestrictionAndSetDisabled(
1010                                 UserManager.DISALLOW_DATA_ROAMING);
1011                     }
1012                 }
1013             }
1014         }
1015 
updateBody()1016         private void updateBody() {
1017             final Activity activity = getActivity();
1018             final PreferenceScreen prefSet = getPreferenceScreen();
1019             final boolean hasActiveSubscriptions = hasActiveSubscriptions();
1020 
1021             if (activity == null || activity.isDestroyed()) {
1022                 Log.e(LOG_TAG, "updateBody with no valid activity.");
1023                 return;
1024             }
1025 
1026             if (prefSet == null) {
1027                 Log.e(LOG_TAG, "updateBody with no null prefSet.");
1028                 return;
1029             }
1030 
1031             prefSet.removeAll();
1032 
1033             updateBodyBasicFields(activity, prefSet, mSubId, hasActiveSubscriptions);
1034 
1035             if (hasActiveSubscriptions) {
1036                 if (mExpandAdvancedFields) {
1037                     updateBodyAdvancedFields(activity, prefSet, mSubId, hasActiveSubscriptions);
1038                 } else {
1039                     prefSet.addPreference(mAdvancedOptions);
1040                 }
1041             } else {
1042                 // Shows the "Carrier" preference that allows user to add a e-sim profile.
1043                 if (showEuiccSettings(getContext())) {
1044                     mEuiccSettingsPref.setSummary(null /* summary */);
1045                     prefSet.addPreference(mEuiccSettingsPref);
1046                 }
1047             }
1048         }
1049 
updateBodyAdvancedFields(Activity activity, PreferenceScreen prefSet, int phoneSubId, boolean hasActiveSubscriptions)1050         private void updateBodyAdvancedFields(Activity activity, PreferenceScreen prefSet,
1051                 int phoneSubId, boolean hasActiveSubscriptions) {
1052             boolean isLteOnCdma = mTelephonyManager.getLteOnCdmaMode()
1053                     == PhoneConstants.LTE_ON_CDMA_TRUE;
1054 
1055             if (DBG) {
1056                 log("updateBody: isLteOnCdma=" + isLteOnCdma + " phoneSubId=" + phoneSubId);
1057             }
1058 
1059             prefSet.addPreference(mButtonPreferredNetworkMode);
1060             prefSet.addPreference(mButtonEnabledNetworks);
1061             prefSet.addPreference(mButton4glte);
1062 
1063             if (showEuiccSettings(getActivity())) {
1064                 prefSet.addPreference(mEuiccSettingsPref);
1065                 String spn = mTelephonyManager.getSimOperatorName();
1066                 if (TextUtils.isEmpty(spn)) {
1067                     mEuiccSettingsPref.setSummary(null);
1068                 } else {
1069                     mEuiccSettingsPref.setSummary(spn);
1070                 }
1071             }
1072 
1073             int settingsNetworkMode = android.provider.Settings.Global.getInt(
1074                     getContext().getContentResolver(),
1075                     android.provider.Settings.Global.PREFERRED_NETWORK_MODE + phoneSubId,
1076                     preferredNetworkMode);
1077 
1078             PersistableBundle carrierConfig = mCarrierConfigManager.getConfigForSubId(mSubId);
1079             mIsGlobalCdma = isLteOnCdma
1080                     && carrierConfig.getBoolean(CarrierConfigManager.KEY_SHOW_CDMA_CHOICES_BOOL);
1081             if (carrierConfig.getBoolean(
1082                     CarrierConfigManager.KEY_HIDE_CARRIER_NETWORK_SETTINGS_BOOL)) {
1083                 prefSet.removePreference(mButtonPreferredNetworkMode);
1084                 prefSet.removePreference(mButtonEnabledNetworks);
1085                 prefSet.removePreference(mLteDataServicePref);
1086             } else if (carrierConfig.getBoolean(CarrierConfigManager
1087                     .KEY_HIDE_PREFERRED_NETWORK_TYPE_BOOL)
1088                     && !mTelephonyManager.getServiceState().getRoaming()
1089                     && mTelephonyManager.getServiceState().getDataRegState()
1090                     == ServiceState.STATE_IN_SERVICE) {
1091                 prefSet.removePreference(mButtonPreferredNetworkMode);
1092                 prefSet.removePreference(mButtonEnabledNetworks);
1093 
1094                 final int phoneType = mTelephonyManager.getPhoneType();
1095                 if (phoneType == PhoneConstants.PHONE_TYPE_CDMA) {
1096                     updateCdmaOptions(this, prefSet, mSubId);
1097                 } else if (phoneType == PhoneConstants.PHONE_TYPE_GSM) {
1098                     updateGsmUmtsOptions(this, prefSet, phoneSubId);
1099                 } else {
1100                     throw new IllegalStateException("Unexpected phone type: " + phoneType);
1101                 }
1102                 // Since pref is being hidden from user, set network mode to default
1103                 // in case it is currently something else. That is possible if user
1104                 // changed the setting while roaming and is now back to home network.
1105                 settingsNetworkMode = preferredNetworkMode;
1106             } else if (carrierConfig.getBoolean(
1107                     CarrierConfigManager.KEY_WORLD_PHONE_BOOL) == true) {
1108                 prefSet.removePreference(mButtonEnabledNetworks);
1109                 // set the listener for the mButtonPreferredNetworkMode list preference so we can issue
1110                 // change Preferred Network Mode.
1111                 mButtonPreferredNetworkMode.setOnPreferenceChangeListener(this);
1112 
1113                 updateCdmaOptions(this, prefSet, mSubId);
1114                 updateGsmUmtsOptions(this, prefSet, phoneSubId);
1115             } else {
1116                 prefSet.removePreference(mButtonPreferredNetworkMode);
1117                 updateEnabledNetworksEntries();
1118                 mButtonEnabledNetworks.setOnPreferenceChangeListener(this);
1119                 if (DBG) log("settingsNetworkMode: " + settingsNetworkMode);
1120             }
1121 
1122             final boolean missingDataServiceUrl = TextUtils.isEmpty(
1123                     android.provider.Settings.Global.getString(activity.getContentResolver(),
1124                             android.provider.Settings.Global.SETUP_PREPAID_DATA_SERVICE_URL));
1125             if (!isLteOnCdma || missingDataServiceUrl) {
1126                 prefSet.removePreference(mLteDataServicePref);
1127             } else {
1128                 android.util.Log.d(LOG_TAG, "keep ltePref");
1129             }
1130 
1131             updateEnhanced4gLteState();
1132             updatePreferredNetworkType();
1133             updateCallingCategory();
1134 
1135             // Enable link to CMAS app settings depending on the value in config.xml.
1136             final boolean isCellBroadcastAppLinkEnabled = activity.getResources().getBoolean(
1137                     com.android.internal.R.bool.config_cellBroadcastAppLinks);
1138             if (!mUm.isAdminUser() || !isCellBroadcastAppLinkEnabled
1139                     || mUm.hasUserRestriction(UserManager.DISALLOW_CONFIG_CELL_BROADCASTS)) {
1140                 PreferenceScreen root = getPreferenceScreen();
1141                 Preference ps = findPreference(BUTTON_CELL_BROADCAST_SETTINGS);
1142                 if (ps != null) {
1143                     root.removePreference(ps);
1144                 }
1145             }
1146 
1147             /**
1148              * Listen to extra preference changes that need as Metrics events logging.
1149              */
1150             if (prefSet.findPreference(BUTTON_CDMA_SYSTEM_SELECT_KEY) != null) {
1151                 prefSet.findPreference(BUTTON_CDMA_SYSTEM_SELECT_KEY)
1152                         .setOnPreferenceChangeListener(this);
1153             }
1154 
1155             if (prefSet.findPreference(BUTTON_CDMA_SUBSCRIPTION_KEY) != null) {
1156                 prefSet.findPreference(BUTTON_CDMA_SUBSCRIPTION_KEY)
1157                         .setOnPreferenceChangeListener(this);
1158             }
1159 
1160             // Get the networkMode from Settings.System and displays it
1161             mButtonEnabledNetworks.setValue(Integer.toString(settingsNetworkMode));
1162             mButtonPreferredNetworkMode.setValue(Integer.toString(settingsNetworkMode));
1163             UpdatePreferredNetworkModeSummary(settingsNetworkMode);
1164             UpdateEnabledNetworksValueAndSummary(settingsNetworkMode);
1165             // Display preferred network type based on what modem returns b/18676277
1166             new SetPreferredNetworkAsyncTask(
1167                     mTelephonyManager,
1168                     mSubId,
1169                     settingsNetworkMode,
1170                     mHandler.obtainMessage(MyHandler.MESSAGE_SET_PREFERRED_NETWORK_TYPE))
1171                     .executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
1172 
1173             /**
1174              * Enable/disable depending upon if there are any active subscriptions.
1175              *
1176              * I've decided to put this enable/disable code at the bottom as the
1177              * code above works even when there are no active subscriptions, thus
1178              * putting it afterwards is a smaller change. This can be refined later,
1179              * but you do need to remember that this all needs to work when subscriptions
1180              * change dynamically such as when hot swapping sims.
1181              */
1182             int variant4glteTitleIndex = carrierConfig.getInt(
1183                     CarrierConfigManager.KEY_ENHANCED_4G_LTE_TITLE_VARIANT_INT);
1184             CharSequence[] variantTitles = getContext().getResources()
1185                     .getTextArray(R.array.enhanced_4g_lte_mode_title_variant);
1186             CharSequence[] variantSumaries = getContext().getResources()
1187                     .getTextArray(R.array.enhanced_4g_lte_mode_sumary_variant);
1188             // Default index 0 indicates the default title/sumary string
1189             CharSequence enhanced4glteModeTitle = variantTitles[0];
1190             CharSequence enhanced4glteModeSummary = variantSumaries[0];
1191             if (variant4glteTitleIndex >= 0 && variant4glteTitleIndex < variantTitles.length) {
1192                 enhanced4glteModeTitle = variantTitles[variant4glteTitleIndex];
1193             }
1194             if (variant4glteTitleIndex >= 0 && variant4glteTitleIndex < variantSumaries.length) {
1195                 enhanced4glteModeSummary = variantSumaries[variant4glteTitleIndex];
1196             }
1197 
1198             mOnlyAutoSelectInHomeNW = carrierConfig.getBoolean(
1199                     CarrierConfigManager.KEY_ONLY_AUTO_SELECT_IN_HOME_NETWORK_BOOL);
1200             mButton4glte.setTitle(enhanced4glteModeTitle);
1201             mButton4glte.setSummary(enhanced4glteModeSummary);
1202             mLteDataServicePref.setEnabled(hasActiveSubscriptions);
1203             Preference ps;
1204             ps = findPreference(BUTTON_CELL_BROADCAST_SETTINGS);
1205             if (ps != null) {
1206                 ps.setEnabled(hasActiveSubscriptions);
1207             }
1208             ps = findPreference(CATEGORY_GSM_APN_EXPAND_KEY);
1209             if (ps != null) {
1210                 ps.setEnabled(hasActiveSubscriptions);
1211             }
1212             ps = findPreference(CATEGORY_CDMA_APN_EXPAND_KEY);
1213             if (ps != null) {
1214                 ps.setEnabled(hasActiveSubscriptions);
1215             }
1216             ps = findPreference(NetworkOperators.CATEGORY_NETWORK_OPERATORS_KEY);
1217             if (ps != null) {
1218                 ps.setEnabled(hasActiveSubscriptions);
1219             }
1220             ps = findPreference(BUTTON_CARRIER_SETTINGS_KEY);
1221             if (ps != null) {
1222                 ps.setEnabled(hasActiveSubscriptions);
1223             }
1224             ps = findPreference(BUTTON_CDMA_SYSTEM_SELECT_KEY);
1225             if (ps != null) {
1226                 ps.setEnabled(hasActiveSubscriptions);
1227             }
1228             ps = findPreference(CATEGORY_CALLING_KEY);
1229             if (ps != null) {
1230                 ps.setEnabled(hasActiveSubscriptions);
1231             }
1232             ps = findPreference(NetworkOperators.BUTTON_AUTO_SELECT_KEY);
1233             if (ps != null) {
1234                 ps.setSummary(null);
1235                 if (mTelephonyManager.getServiceState().getRoaming()) {
1236                     ps.setEnabled(true);
1237                 } else {
1238                     ps.setEnabled(!mOnlyAutoSelectInHomeNW);
1239                     if (mOnlyAutoSelectInHomeNW) {
1240                         ps.setSummary(getResources().getString(
1241                                 R.string.manual_mode_disallowed_summary,
1242                                 mTelephonyManager.getSimOperatorName()));
1243                     }
1244                 }
1245             }
1246         }
1247 
1248         // Requires that mSubId is up to date
updateEnabledNetworksEntries()1249         void updateEnabledNetworksEntries() {
1250             final int phoneType = mTelephonyManager.getPhoneType();
1251             final PersistableBundle carrierConfig = mCarrierConfigManager.getConfigForSubId(mSubId);
1252             mShow4GForLTE = carrierConfig != null ? carrierConfig.getBoolean(
1253                     CarrierConfigManager.KEY_SHOW_4G_FOR_LTE_DATA_ICON_BOOL) : false;
1254             if (phoneType == PhoneConstants.PHONE_TYPE_CDMA) {
1255                 final int lteForced = android.provider.Settings.Global.getInt(
1256                         getContext().getContentResolver(),
1257                         android.provider.Settings.Global.LTE_SERVICE_FORCED + mSubId,
1258                         0);
1259                 final boolean isLteOnCdma = mTelephonyManager.getLteOnCdmaMode()
1260                         == PhoneConstants.LTE_ON_CDMA_TRUE;
1261                 final int settingsNetworkMode = android.provider.Settings.Global.getInt(
1262                         getContext().getContentResolver(),
1263                         android.provider.Settings.Global.PREFERRED_NETWORK_MODE + mSubId,
1264                         preferredNetworkMode);
1265                 if (isLteOnCdma) {
1266                     if (lteForced == 0) {
1267                         mButtonEnabledNetworks.setEntries(
1268                                 R.array.enabled_networks_cdma_choices);
1269                         mButtonEnabledNetworks.setEntryValues(
1270                                 R.array.enabled_networks_cdma_values);
1271                     } else {
1272                         switch (settingsNetworkMode) {
1273                             case TelephonyManager.NETWORK_MODE_CDMA_EVDO:
1274                             case TelephonyManager.NETWORK_MODE_CDMA_NO_EVDO:
1275                             case TelephonyManager.NETWORK_MODE_EVDO_NO_CDMA:
1276                                 mButtonEnabledNetworks.setEntries(
1277                                         R.array.enabled_networks_cdma_no_lte_choices);
1278                                 mButtonEnabledNetworks.setEntryValues(
1279                                         R.array.enabled_networks_cdma_no_lte_values);
1280                                 break;
1281                             case TelephonyManager.NETWORK_MODE_GLOBAL:
1282                             case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO:
1283                             case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA:
1284                             case TelephonyManager.NETWORK_MODE_LTE_ONLY:
1285                                 mButtonEnabledNetworks.setEntries(
1286                                         R.array.enabled_networks_cdma_only_lte_choices);
1287                                 mButtonEnabledNetworks.setEntryValues(
1288                                         R.array.enabled_networks_cdma_only_lte_values);
1289                                 break;
1290                             default:
1291                                 mButtonEnabledNetworks.setEntries(
1292                                         R.array.enabled_networks_cdma_choices);
1293                                 mButtonEnabledNetworks.setEntryValues(
1294                                         R.array.enabled_networks_cdma_values);
1295                                 break;
1296                         }
1297                     }
1298                 }
1299                 updateCdmaOptions(this, getPreferenceScreen(), mSubId);
1300 
1301             } else if (phoneType == PhoneConstants.PHONE_TYPE_GSM) {
1302                 if (isSupportTdscdma()) {
1303                     mButtonEnabledNetworks.setEntries(
1304                             R.array.enabled_networks_tdscdma_choices);
1305                     mButtonEnabledNetworks.setEntryValues(
1306                             R.array.enabled_networks_tdscdma_values);
1307                 } else if (!carrierConfig.getBoolean(CarrierConfigManager.KEY_PREFER_2G_BOOL)
1308                         && !getResources().getBoolean(R.bool.config_enabled_lte)) {
1309                     mButtonEnabledNetworks.setEntries(
1310                             R.array.enabled_networks_except_gsm_lte_choices);
1311                     mButtonEnabledNetworks.setEntryValues(
1312                             R.array.enabled_networks_except_gsm_lte_values);
1313                 } else if (!carrierConfig.getBoolean(CarrierConfigManager.KEY_PREFER_2G_BOOL)) {
1314                     int select = mShow4GForLTE
1315                             ? R.array.enabled_networks_except_gsm_4g_choices
1316                             : R.array.enabled_networks_except_gsm_choices;
1317                     mButtonEnabledNetworks.setEntries(select);
1318                     mButtonEnabledNetworks.setEntryValues(
1319                             R.array.enabled_networks_except_gsm_values);
1320                 } else if (!getResources().getBoolean(R.bool.config_enabled_lte)) {
1321                     mButtonEnabledNetworks.setEntries(
1322                             R.array.enabled_networks_except_lte_choices);
1323                     mButtonEnabledNetworks.setEntryValues(
1324                             R.array.enabled_networks_except_lte_values);
1325                 } else if (mIsGlobalCdma) {
1326                     mButtonEnabledNetworks.setEntries(
1327                             R.array.enabled_networks_cdma_choices);
1328                     mButtonEnabledNetworks.setEntryValues(
1329                             R.array.enabled_networks_cdma_values);
1330                 } else {
1331                     int select = mShow4GForLTE ? R.array.enabled_networks_4g_choices
1332                             : R.array.enabled_networks_choices;
1333                     mButtonEnabledNetworks.setEntries(select);
1334                     mButtonEnabledNetworks.setEntryValues(
1335                             R.array.enabled_networks_values);
1336                 }
1337                 updateGsmUmtsOptions(this, getPreferenceScreen(), mSubId);
1338             } else {
1339                 throw new IllegalStateException("Unexpected phone type: " + phoneType);
1340             }
1341             if (isWorldMode()) {
1342                 mButtonEnabledNetworks.setEntries(
1343                         R.array.preferred_network_mode_choices_world_mode);
1344                 mButtonEnabledNetworks.setEntryValues(
1345                         R.array.preferred_network_mode_values_world_mode);
1346             }
1347         }
1348 
1349         @Override
onPause()1350         public void onPause() {
1351             super.onPause();
1352             if (DBG) log("onPause:+");
1353 
1354             mTelephonyManager.listen(mPhoneStateListener, PhoneStateListener.LISTEN_NONE);
1355 
1356             mSubscriptionManager
1357                     .removeOnSubscriptionsChangedListener(mOnSubscriptionsChangeListener);
1358 
1359             final Context context = getActivity();
1360             context.unregisterReceiver(mPhoneChangeReceiver);
1361             context.getContentResolver().unregisterContentObserver(mDpcEnforcedContentObserver);
1362 
1363             // Remove callback for provisioning changes.
1364             try {
1365                 if (mImsMgr != null) {
1366                     mImsMgr.getConfigInterface().removeConfigCallback(
1367                             mProvisioningCallback.getBinder());
1368                 }
1369             } catch (ImsException e) {
1370                 Log.w(LOG_TAG, "onPause: Unable to remove callback for provisioning changes");
1371             }
1372 
1373             if (DBG) log("onPause:-");
1374         }
1375 
1376         /**
1377          * Implemented to support onPreferenceChangeListener to look for preference
1378          * changes specifically on CLIR.
1379          *
1380          * @param preference is the preference to be changed, should be mButtonCLIR.
1381          * @param objValue should be the value of the selection, NOT its localized
1382          * display value.
1383          */
onPreferenceChange(Preference preference, Object objValue)1384         public boolean onPreferenceChange(Preference preference, Object objValue) {
1385             sendMetricsEventPreferenceChanged(getPreferenceScreen(), preference, objValue);
1386 
1387             final int phoneSubId = mSubId;
1388             if (preference == mButtonPreferredNetworkMode) {
1389                 //NOTE onPreferenceChange seems to be called even if there is no change
1390                 //Check if the button value is changed from the System.Setting
1391                 mButtonPreferredNetworkMode.setValue((String) objValue);
1392                 int buttonNetworkMode;
1393                 buttonNetworkMode = Integer.parseInt((String) objValue);
1394                 int settingsNetworkMode = android.provider.Settings.Global.getInt(
1395                         getContext().getContentResolver(),
1396                         android.provider.Settings.Global.PREFERRED_NETWORK_MODE + phoneSubId,
1397                         preferredNetworkMode);
1398                 if (buttonNetworkMode != settingsNetworkMode) {
1399                     int modemNetworkMode;
1400                     // if new mode is invalid ignore it
1401                     switch (buttonNetworkMode) {
1402                         case TelephonyManager.NETWORK_MODE_WCDMA_PREF:
1403                         case TelephonyManager.NETWORK_MODE_GSM_ONLY:
1404                         case TelephonyManager.NETWORK_MODE_WCDMA_ONLY:
1405                         case TelephonyManager.NETWORK_MODE_GSM_UMTS:
1406                         case TelephonyManager.NETWORK_MODE_CDMA_EVDO:
1407                         case TelephonyManager.NETWORK_MODE_CDMA_NO_EVDO:
1408                         case TelephonyManager.NETWORK_MODE_EVDO_NO_CDMA:
1409                         case TelephonyManager.NETWORK_MODE_GLOBAL:
1410                         case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO:
1411                         case TelephonyManager.NETWORK_MODE_LTE_GSM_WCDMA:
1412                         case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA:
1413                         case TelephonyManager.NETWORK_MODE_LTE_ONLY:
1414                         case TelephonyManager.NETWORK_MODE_LTE_WCDMA:
1415                         case TelephonyManager.NETWORK_MODE_TDSCDMA_ONLY:
1416                         case TelephonyManager.NETWORK_MODE_TDSCDMA_WCDMA:
1417                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA:
1418                         case TelephonyManager.NETWORK_MODE_TDSCDMA_GSM:
1419                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_GSM:
1420                         case TelephonyManager.NETWORK_MODE_TDSCDMA_GSM_WCDMA:
1421                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_WCDMA:
1422                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_GSM_WCDMA:
1423                         case TelephonyManager.NETWORK_MODE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1424                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1425                             // This is one of the modes we recognize
1426                             modemNetworkMode = buttonNetworkMode;
1427                             break;
1428                         default:
1429                             loge("Invalid Network Mode (" +buttonNetworkMode+ ") chosen. Ignore.");
1430                             return true;
1431                     }
1432 
1433                     android.provider.Settings.Global.putInt(
1434                             getContext().getContentResolver(),
1435                             android.provider.Settings.Global.PREFERRED_NETWORK_MODE + phoneSubId,
1436                             buttonNetworkMode );
1437                     //Set the modem network mode
1438                     new SetPreferredNetworkAsyncTask(
1439                             mTelephonyManager,
1440                             mSubId,
1441                             modemNetworkMode,
1442                             mHandler.obtainMessage(MyHandler.MESSAGE_SET_PREFERRED_NETWORK_TYPE))
1443                             .executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
1444                 }
1445             } else if (preference == mButtonEnabledNetworks) {
1446                 mButtonEnabledNetworks.setValue((String) objValue);
1447                 int buttonNetworkMode;
1448                 buttonNetworkMode = Integer.parseInt((String) objValue);
1449                 if (DBG) log("buttonNetworkMode: " + buttonNetworkMode);
1450                 int settingsNetworkMode = android.provider.Settings.Global.getInt(
1451                         getContext().getContentResolver(),
1452                         android.provider.Settings.Global.PREFERRED_NETWORK_MODE + phoneSubId,
1453                         preferredNetworkMode);
1454                 if (buttonNetworkMode != settingsNetworkMode) {
1455                     int modemNetworkMode;
1456                     // if new mode is invalid ignore it
1457                     switch (buttonNetworkMode) {
1458                         case TelephonyManager.NETWORK_MODE_WCDMA_PREF:
1459                         case TelephonyManager.NETWORK_MODE_GSM_ONLY:
1460                         case TelephonyManager.NETWORK_MODE_LTE_GSM_WCDMA:
1461                         case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA:
1462                         case TelephonyManager.NETWORK_MODE_CDMA_EVDO:
1463                         case TelephonyManager.NETWORK_MODE_CDMA_NO_EVDO:
1464                         case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO:
1465                         case TelephonyManager.NETWORK_MODE_TDSCDMA_ONLY:
1466                         case TelephonyManager.NETWORK_MODE_TDSCDMA_WCDMA:
1467                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA:
1468                         case TelephonyManager.NETWORK_MODE_TDSCDMA_GSM:
1469                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_GSM:
1470                         case TelephonyManager.NETWORK_MODE_TDSCDMA_GSM_WCDMA:
1471                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_WCDMA:
1472                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_GSM_WCDMA:
1473                         case TelephonyManager.NETWORK_MODE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1474                         case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1475                             // This is one of the modes we recognize
1476                             modemNetworkMode = buttonNetworkMode;
1477                             break;
1478                         default:
1479                             loge("Invalid Network Mode (" +buttonNetworkMode+ ") chosen. Ignore.");
1480                             return true;
1481                     }
1482 
1483                     UpdateEnabledNetworksValueAndSummary(buttonNetworkMode);
1484 
1485                     android.provider.Settings.Global.putInt(
1486                             getContext().getContentResolver(),
1487                             android.provider.Settings.Global.PREFERRED_NETWORK_MODE + phoneSubId,
1488                             buttonNetworkMode );
1489                     //Set the modem network mode
1490                     new SetPreferredNetworkAsyncTask(
1491                             mTelephonyManager,
1492                             mSubId,
1493                             modemNetworkMode,
1494                             mHandler.obtainMessage(MyHandler.MESSAGE_SET_PREFERRED_NETWORK_TYPE))
1495                             .executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
1496                 }
1497             } else if (preference == mButton4glte) {
1498                 boolean enhanced4gMode = !mButton4glte.isChecked();
1499                 mButton4glte.setChecked(enhanced4gMode);
1500                 mImsMgr.setEnhanced4gLteModeSetting(mButton4glte.isChecked());
1501             } else if (preference == mButtonDataRoam) {
1502                 if (DBG) log("onPreferenceTreeClick: preference == mButtonDataRoam.");
1503 
1504                 //normally called on the toggle click
1505                 if (!mButtonDataRoam.isChecked()) {
1506                     PersistableBundle carrierConfig = mCarrierConfigManager.getConfigForSubId(
1507                             mSubId);
1508                     if (carrierConfig != null && carrierConfig.getBoolean(
1509                             CarrierConfigManager.KEY_DISABLE_CHARGE_INDICATION_BOOL)) {
1510                         mTelephonyManager.setDataRoamingEnabled(true);
1511                         MetricsLogger.action(getContext(),
1512                                 getMetricsEventCategory(getPreferenceScreen(), mButtonDataRoam),
1513                                 true);
1514                     } else {
1515                         // MetricsEvent with no value update.
1516                         MetricsLogger.action(getContext(),
1517                                 getMetricsEventCategory(getPreferenceScreen(), mButtonDataRoam));
1518                         // First confirm with a warning dialog about charges
1519                         mOkClicked = false;
1520                         RoamingDialogFragment fragment = new RoamingDialogFragment();
1521                         Bundle b = new Bundle();
1522                         b.putInt(RoamingDialogFragment.SUB_ID_KEY, mSubId);
1523                         fragment.setArguments(b);
1524                         fragment.show(getFragmentManager(), ROAMING_TAG);
1525                         // Don't update the toggle unless the confirm button is actually pressed.
1526                         return false;
1527                     }
1528                 } else {
1529                     mTelephonyManager.setDataRoamingEnabled(false);
1530                     MetricsLogger.action(getContext(),
1531                             getMetricsEventCategory(getPreferenceScreen(), mButtonDataRoam),
1532                             false);
1533                     return true;
1534                 }
1535             } else if (preference == mVideoCallingPref) {
1536                 // If mButton4glte is not checked, mVideoCallingPref should be disabled.
1537                 // So it only makes sense to call phoneMgr.enableVideoCalling if it's checked.
1538                 if (mButton4glte.isChecked()) {
1539                     mImsMgr.setVtSetting((boolean) objValue);
1540                     return true;
1541                 } else {
1542                     loge("mVideoCallingPref should be disabled if mButton4glte is not checked.");
1543                     mVideoCallingPref.setEnabled(false);
1544                     return false;
1545                 }
1546             } else if (preference == getPreferenceScreen()
1547                     .findPreference(BUTTON_CDMA_SYSTEM_SELECT_KEY)
1548                     || preference == getPreferenceScreen()
1549                     .findPreference(BUTTON_CDMA_SUBSCRIPTION_KEY)) {
1550                 return true;
1551             }
1552 
1553             updateBody();
1554             // always let the preference setting proceed.
1555             return true;
1556         }
1557 
is4gLtePrefEnabled(PersistableBundle carrierConfig)1558         private boolean is4gLtePrefEnabled(PersistableBundle carrierConfig) {
1559             return (mTelephonyManager.getCallState(mSubId)
1560                     == TelephonyManager.CALL_STATE_IDLE)
1561                     && mImsMgr != null
1562                     && mImsMgr.isNonTtyOrTtyOnVolteEnabled()
1563                     && carrierConfig.getBoolean(
1564                             CarrierConfigManager.KEY_EDITABLE_ENHANCED_4G_LTE_BOOL);
1565         }
1566 
1567         private class MyHandler extends Handler {
1568 
1569             static final int MESSAGE_SET_PREFERRED_NETWORK_TYPE = 0;
1570 
1571             @Override
handleMessage(Message msg)1572             public void handleMessage(Message msg) {
1573                 switch (msg.what) {
1574                     case MESSAGE_SET_PREFERRED_NETWORK_TYPE:
1575                         handleSetPreferredNetworkTypeResponse(msg);
1576                         break;
1577                 }
1578             }
1579 
handleSetPreferredNetworkTypeResponse(Message msg)1580             private void handleSetPreferredNetworkTypeResponse(Message msg) {
1581                 final Activity activity = getActivity();
1582                 if (activity == null || activity.isDestroyed()) {
1583                     // Access preferences of activity only if it is not destroyed
1584                     // or if fragment is not attached to an activity.
1585                     return;
1586                 }
1587 
1588                 boolean success = (boolean) msg.obj;
1589 
1590                 if (success) {
1591                     int networkMode;
1592                     if (getPreferenceScreen().findPreference(
1593                             BUTTON_PREFERED_NETWORK_MODE) != null)  {
1594                         networkMode =  Integer.parseInt(mButtonPreferredNetworkMode.getValue());
1595                         android.provider.Settings.Global.putInt(
1596                                 getContext().getContentResolver(),
1597                                 android.provider.Settings.Global.PREFERRED_NETWORK_MODE
1598                                         + mSubId,
1599                                 networkMode );
1600                     }
1601                     if (getPreferenceScreen().findPreference(BUTTON_ENABLED_NETWORKS_KEY) != null) {
1602                         networkMode = Integer.parseInt(mButtonEnabledNetworks.getValue());
1603                         android.provider.Settings.Global.putInt(
1604                                 getContext().getContentResolver(),
1605                                 android.provider.Settings.Global.PREFERRED_NETWORK_MODE
1606                                         + mSubId,
1607                                 networkMode );
1608                     }
1609                 } else {
1610                     Log.i(LOG_TAG, "handleSetPreferredNetworkTypeResponse:" +
1611                             "exception in setting network mode.");
1612                     updatePreferredNetworkUIFromDb();
1613                 }
1614             }
1615         }
1616 
updatePreferredNetworkUIFromDb()1617         private void updatePreferredNetworkUIFromDb() {
1618             int settingsNetworkMode = android.provider.Settings.Global.getInt(
1619                     getContext().getContentResolver(),
1620                     android.provider.Settings.Global.PREFERRED_NETWORK_MODE + mSubId,
1621                     preferredNetworkMode);
1622 
1623             if (DBG) {
1624                 log("updatePreferredNetworkUIFromDb: settingsNetworkMode = " +
1625                         settingsNetworkMode);
1626             }
1627 
1628             UpdatePreferredNetworkModeSummary(settingsNetworkMode);
1629             UpdateEnabledNetworksValueAndSummary(settingsNetworkMode);
1630             // changes the mButtonPreferredNetworkMode accordingly to settingsNetworkMode
1631             mButtonPreferredNetworkMode.setValue(Integer.toString(settingsNetworkMode));
1632         }
1633 
UpdatePreferredNetworkModeSummary(int NetworkMode)1634         private void UpdatePreferredNetworkModeSummary(int NetworkMode) {
1635             switch(NetworkMode) {
1636                 case TelephonyManager.NETWORK_MODE_TDSCDMA_GSM_WCDMA:
1637                     mButtonPreferredNetworkMode.setSummary(
1638                             R.string.preferred_network_mode_tdscdma_gsm_wcdma_summary);
1639                     break;
1640                 case TelephonyManager.NETWORK_MODE_TDSCDMA_GSM:
1641                     mButtonPreferredNetworkMode.setSummary(
1642                             R.string.preferred_network_mode_tdscdma_gsm_summary);
1643                     break;
1644                 case TelephonyManager.NETWORK_MODE_WCDMA_PREF:
1645                     mButtonPreferredNetworkMode.setSummary(
1646                             R.string.preferred_network_mode_wcdma_perf_summary);
1647                     break;
1648                 case TelephonyManager.NETWORK_MODE_GSM_ONLY:
1649                     mButtonPreferredNetworkMode.setSummary(
1650                             R.string.preferred_network_mode_gsm_only_summary);
1651                     break;
1652                 case TelephonyManager.NETWORK_MODE_TDSCDMA_WCDMA:
1653                     mButtonPreferredNetworkMode.setSummary(
1654                             R.string.preferred_network_mode_tdscdma_wcdma_summary);
1655                     break;
1656                 case TelephonyManager.NETWORK_MODE_WCDMA_ONLY:
1657                     mButtonPreferredNetworkMode.setSummary(
1658                             R.string.preferred_network_mode_wcdma_only_summary);
1659                     break;
1660                 case TelephonyManager.NETWORK_MODE_GSM_UMTS:
1661                     mButtonPreferredNetworkMode.setSummary(
1662                             R.string.preferred_network_mode_gsm_wcdma_summary);
1663                     break;
1664                 case TelephonyManager.NETWORK_MODE_CDMA_EVDO:
1665                     switch (mTelephonyManager.getLteOnCdmaMode()) {
1666                         case PhoneConstants.LTE_ON_CDMA_TRUE:
1667                             mButtonPreferredNetworkMode.setSummary(
1668                                     R.string.preferred_network_mode_cdma_summary);
1669                             break;
1670                         case PhoneConstants.LTE_ON_CDMA_FALSE:
1671                         default:
1672                             mButtonPreferredNetworkMode.setSummary(
1673                                     R.string.preferred_network_mode_cdma_evdo_summary);
1674                             break;
1675                     }
1676                     break;
1677                 case TelephonyManager.NETWORK_MODE_CDMA_NO_EVDO:
1678                     mButtonPreferredNetworkMode.setSummary(
1679                             R.string.preferred_network_mode_cdma_only_summary);
1680                     break;
1681                 case TelephonyManager.NETWORK_MODE_EVDO_NO_CDMA:
1682                     mButtonPreferredNetworkMode.setSummary(
1683                             R.string.preferred_network_mode_evdo_only_summary);
1684                     break;
1685                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA:
1686                     mButtonPreferredNetworkMode.setSummary(
1687                             R.string.preferred_network_mode_lte_tdscdma_summary);
1688                     break;
1689                 case TelephonyManager.NETWORK_MODE_LTE_ONLY:
1690                     mButtonPreferredNetworkMode.setSummary(
1691                             R.string.preferred_network_mode_lte_summary);
1692                     break;
1693                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_GSM:
1694                     mButtonPreferredNetworkMode.setSummary(
1695                             R.string.preferred_network_mode_lte_tdscdma_gsm_summary);
1696                     break;
1697                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_GSM_WCDMA:
1698                     mButtonPreferredNetworkMode.setSummary(
1699                             R.string.preferred_network_mode_lte_tdscdma_gsm_wcdma_summary);
1700                     break;
1701                 case TelephonyManager.NETWORK_MODE_LTE_GSM_WCDMA:
1702                     mButtonPreferredNetworkMode.setSummary(
1703                             R.string.preferred_network_mode_lte_gsm_wcdma_summary);
1704                     break;
1705                 case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO:
1706                     mButtonPreferredNetworkMode.setSummary(
1707                             R.string.preferred_network_mode_lte_cdma_evdo_summary);
1708                     break;
1709                 case TelephonyManager.NETWORK_MODE_TDSCDMA_ONLY:
1710                     mButtonPreferredNetworkMode.setSummary(
1711                             R.string.preferred_network_mode_tdscdma_summary);
1712                     break;
1713                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1714                     mButtonPreferredNetworkMode.setSummary(
1715                             R.string.preferred_network_mode_lte_tdscdma_cdma_evdo_gsm_wcdma_summary);
1716                     break;
1717                 case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA:
1718                     if (mTelephonyManager.getPhoneType() == PhoneConstants.PHONE_TYPE_CDMA
1719                             || mIsGlobalCdma
1720                             || isWorldMode()) {
1721                         mButtonPreferredNetworkMode.setSummary(
1722                                 R.string.preferred_network_mode_global_summary);
1723                     } else {
1724                         mButtonPreferredNetworkMode.setSummary(
1725                                 R.string.preferred_network_mode_lte_summary);
1726                     }
1727                     break;
1728                 case TelephonyManager.NETWORK_MODE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1729                     mButtonPreferredNetworkMode.setSummary(
1730                             R.string.preferred_network_mode_tdscdma_cdma_evdo_gsm_wcdma_summary);
1731                     break;
1732                 case TelephonyManager.NETWORK_MODE_GLOBAL:
1733                     mButtonPreferredNetworkMode.setSummary(
1734                             R.string.preferred_network_mode_cdma_evdo_gsm_wcdma_summary);
1735                     break;
1736                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_WCDMA:
1737                     mButtonPreferredNetworkMode.setSummary(
1738                             R.string.preferred_network_mode_lte_tdscdma_wcdma_summary);
1739                     break;
1740                 case TelephonyManager.NETWORK_MODE_LTE_WCDMA:
1741                     mButtonPreferredNetworkMode.setSummary(
1742                             R.string.preferred_network_mode_lte_wcdma_summary);
1743                     break;
1744                 default:
1745                     mButtonPreferredNetworkMode.setSummary(
1746                             R.string.preferred_network_mode_global_summary);
1747             }
1748         }
1749 
UpdateEnabledNetworksValueAndSummary(int NetworkMode)1750         private void UpdateEnabledNetworksValueAndSummary(int NetworkMode) {
1751             switch (NetworkMode) {
1752                 case TelephonyManager.NETWORK_MODE_TDSCDMA_WCDMA:
1753                 case TelephonyManager.NETWORK_MODE_TDSCDMA_GSM_WCDMA:
1754                 case TelephonyManager.NETWORK_MODE_TDSCDMA_GSM:
1755                     mButtonEnabledNetworks.setValue(
1756                             Integer.toString(TelephonyManager.NETWORK_MODE_TDSCDMA_GSM_WCDMA));
1757                     mButtonEnabledNetworks.setSummary(R.string.network_3G);
1758                     break;
1759                 case TelephonyManager.NETWORK_MODE_WCDMA_ONLY:
1760                 case TelephonyManager.NETWORK_MODE_GSM_UMTS:
1761                 case TelephonyManager.NETWORK_MODE_WCDMA_PREF:
1762                     if (!mIsGlobalCdma) {
1763                         mButtonEnabledNetworks.setValue(
1764                                 Integer.toString(TelephonyManager.NETWORK_MODE_WCDMA_PREF));
1765                         mButtonEnabledNetworks.setSummary(R.string.network_3G);
1766                     } else {
1767                         mButtonEnabledNetworks.setValue(
1768                                 Integer.toString(TelephonyManager
1769                                         .NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA));
1770                         mButtonEnabledNetworks.setSummary(R.string.network_global);
1771                     }
1772                     break;
1773                 case TelephonyManager.NETWORK_MODE_GSM_ONLY:
1774                     if (!mIsGlobalCdma) {
1775                         mButtonEnabledNetworks.setValue(
1776                                 Integer.toString(TelephonyManager.NETWORK_MODE_GSM_ONLY));
1777                         mButtonEnabledNetworks.setSummary(R.string.network_2G);
1778                     } else {
1779                         mButtonEnabledNetworks.setValue(
1780                                 Integer.toString(TelephonyManager
1781                                         .NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA));
1782                         mButtonEnabledNetworks.setSummary(R.string.network_global);
1783                     }
1784                     break;
1785                 case TelephonyManager.NETWORK_MODE_LTE_GSM_WCDMA:
1786                     if (isWorldMode()) {
1787                         mButtonEnabledNetworks.setSummary(
1788                                 R.string.preferred_network_mode_lte_gsm_umts_summary);
1789                         controlCdmaOptions(false);
1790                         controlGsmOptions(true);
1791                         break;
1792                     }
1793                 case TelephonyManager.NETWORK_MODE_LTE_ONLY:
1794                 case TelephonyManager.NETWORK_MODE_LTE_WCDMA:
1795                     if (!mIsGlobalCdma) {
1796                         mButtonEnabledNetworks.setValue(
1797                                 Integer.toString(TelephonyManager.NETWORK_MODE_LTE_GSM_WCDMA));
1798                         mButtonEnabledNetworks.setSummary((mShow4GForLTE == true)
1799                                 ? R.string.network_4G : R.string.network_lte);
1800                     } else {
1801                         mButtonEnabledNetworks.setValue(
1802                                 Integer.toString(TelephonyManager
1803                                         .NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA));
1804                         mButtonEnabledNetworks.setSummary(R.string.network_global);
1805                     }
1806                     break;
1807                 case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO:
1808                     if (isWorldMode()) {
1809                         mButtonEnabledNetworks.setSummary(
1810                                 R.string.preferred_network_mode_lte_cdma_summary);
1811                         controlCdmaOptions(true);
1812                         controlGsmOptions(false);
1813                     } else {
1814                         mButtonEnabledNetworks.setValue(
1815                                 Integer.toString(TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO));
1816                         mButtonEnabledNetworks.setSummary(R.string.network_lte);
1817                     }
1818                     break;
1819                 case TelephonyManager.NETWORK_MODE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1820                     mButtonEnabledNetworks.setValue(
1821                             Integer.toString(TelephonyManager
1822                                     .NETWORK_MODE_TDSCDMA_CDMA_EVDO_GSM_WCDMA));
1823                     mButtonEnabledNetworks.setSummary(R.string.network_3G);
1824                     break;
1825                 case TelephonyManager.NETWORK_MODE_CDMA_EVDO:
1826                 case TelephonyManager.NETWORK_MODE_EVDO_NO_CDMA:
1827                 case TelephonyManager.NETWORK_MODE_GLOBAL:
1828                     mButtonEnabledNetworks.setValue(
1829                             Integer.toString(TelephonyManager.NETWORK_MODE_CDMA_EVDO));
1830                     mButtonEnabledNetworks.setSummary(R.string.network_3G);
1831                     break;
1832                 case TelephonyManager.NETWORK_MODE_CDMA_NO_EVDO:
1833                     mButtonEnabledNetworks.setValue(
1834                             Integer.toString(TelephonyManager.NETWORK_MODE_CDMA_NO_EVDO));
1835                     mButtonEnabledNetworks.setSummary(R.string.network_1x);
1836                     break;
1837                 case TelephonyManager.NETWORK_MODE_TDSCDMA_ONLY:
1838                     mButtonEnabledNetworks.setValue(
1839                             Integer.toString(TelephonyManager.NETWORK_MODE_TDSCDMA_ONLY));
1840                     mButtonEnabledNetworks.setSummary(R.string.network_3G);
1841                     break;
1842                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_GSM:
1843                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_GSM_WCDMA:
1844                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA:
1845                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_WCDMA:
1846                 case TelephonyManager.NETWORK_MODE_LTE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1847                 case TelephonyManager.NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA:
1848                     if (isSupportTdscdma()) {
1849                         mButtonEnabledNetworks.setValue(
1850                                 Integer.toString(TelephonyManager
1851                                         .NETWORK_MODE_LTE_TDSCDMA_CDMA_EVDO_GSM_WCDMA));
1852                         mButtonEnabledNetworks.setSummary(R.string.network_lte);
1853                     } else {
1854                         if (isWorldMode()) {
1855                             controlCdmaOptions(true);
1856                             controlGsmOptions(false);
1857                         }
1858                         mButtonEnabledNetworks.setValue(
1859                                 Integer.toString(TelephonyManager
1860                                         .NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA));
1861                         if (mTelephonyManager.getPhoneType() == PhoneConstants.PHONE_TYPE_CDMA
1862                                 || mIsGlobalCdma
1863                                 || isWorldMode()) {
1864                             mButtonEnabledNetworks.setSummary(R.string.network_global);
1865                         } else {
1866                             mButtonEnabledNetworks.setSummary((mShow4GForLTE == true)
1867                                     ? R.string.network_4G : R.string.network_lte);
1868                         }
1869                     }
1870                     break;
1871                 default:
1872                     String errMsg = "Invalid Network Mode (" + NetworkMode + "). Ignore.";
1873                     loge(errMsg);
1874                     mButtonEnabledNetworks.setSummary(errMsg);
1875             }
1876         }
1877 
1878         @Override
onActivityResult(int requestCode, int resultCode, Intent data)1879         public void onActivityResult(int requestCode, int resultCode, Intent data) {
1880             switch(requestCode) {
1881                 case REQUEST_CODE_EXIT_ECM:
1882                     if (resultCode != Activity.RESULT_CANCELED) {
1883                         // If the phone exits from ECM mode, show the CDMA Options
1884                         mCdmaOptions.showDialog(mClickedPreference);
1885                     }
1886                     break;
1887 
1888                 default:
1889                     break;
1890             }
1891         }
1892 
updateWiFiCallState()1893         private void updateWiFiCallState() {
1894             if (mWiFiCallingPref == null || mCallingCategory == null) {
1895                 return;
1896             }
1897 
1898             // Removes the preference if the wifi calling is disabled.
1899             if (!isWifiCallingEnabled(getContext(), mSubId)) {
1900                 mCallingCategory.removePreference(mWiFiCallingPref);
1901                 return;
1902             }
1903 
1904             // See what Telecom thinks the SIM call manager is.
1905             final PhoneAccountHandle simCallManager =
1906                     TelecomManager.from(getContext()).getSimCallManagerForSubscription(mSubId);
1907 
1908             // Check which SIM call manager is for the current sub ID.
1909             PersistableBundle carrierConfig = mCarrierConfigManager.getConfigForSubId(mSubId);
1910             String currentSubSimCallManager = null;
1911             if (carrierConfig != null) {
1912                 currentSubSimCallManager = carrierConfig.getString(
1913                         CarrierConfigManager.KEY_DEFAULT_SIM_CALL_MANAGER_STRING);
1914             }
1915 
1916             // Only try to configure the phone account if this is the sim call manager for the
1917             // current sub.
1918             if (simCallManager != null
1919                     && simCallManager.getComponentName().flattenToString().equals(
1920                     currentSubSimCallManager)) {
1921                 Intent intent = MobileNetworkSettings.buildPhoneAccountConfigureIntent(
1922                         getContext(), simCallManager);
1923                 PackageManager pm = getContext().getPackageManager();
1924                 List<ResolveInfo> resolutions = pm.queryIntentActivities(intent, 0);
1925                 mWiFiCallingPref.setTitle(resolutions.get(0).loadLabel(pm));
1926                 mWiFiCallingPref.setSummary(null);
1927                 mWiFiCallingPref.setIntent(intent);
1928             } else {
1929                 String title = SubscriptionManager.getResourcesForSubId(getContext(), mSubId)
1930                         .getString(R.string.wifi_calling_settings_title);
1931                 mWiFiCallingPref.setTitle(title);
1932 
1933                 int resId = com.android.internal.R.string.wifi_calling_off_summary;
1934                 if (mImsMgr.isWfcEnabledByUser()) {
1935                     boolean isRoaming = mTelephonyManager.isNetworkRoaming();
1936                     int wfcMode = mImsMgr.getWfcMode(isRoaming);
1937 
1938                     switch (wfcMode) {
1939                         case ImsConfig.WfcModeFeatureValueConstants.WIFI_ONLY:
1940                             resId = com.android.internal.R.string.wfc_mode_wifi_only_summary;
1941                             break;
1942                         case ImsConfig.WfcModeFeatureValueConstants.CELLULAR_PREFERRED:
1943                             resId = com.android.internal.R.string
1944                                     .wfc_mode_cellular_preferred_summary;
1945                             break;
1946                         case ImsConfig.WfcModeFeatureValueConstants.WIFI_PREFERRED:
1947                             resId = com.android.internal.R.string.wfc_mode_wifi_preferred_summary;
1948                             break;
1949                         default:
1950                             if (DBG) log("Unexpected WFC mode value: " + wfcMode);
1951                     }
1952                 }
1953                 mWiFiCallingPref.setSummary(resId);
1954             }
1955 
1956             mCallingCategory.addPreference(mWiFiCallingPref);
1957             mWiFiCallingPref.setEnabled(mTelephonyManager.getCallState(mSubId)
1958                     == TelephonyManager.CALL_STATE_IDLE && hasActiveSubscriptions());
1959         }
1960 
updateEnhanced4gLteState()1961         private void updateEnhanced4gLteState() {
1962             if (mButton4glte == null) {
1963                 return;
1964             }
1965 
1966             PersistableBundle carrierConfig = mCarrierConfigManager.getConfigForSubId(mSubId);
1967 
1968             if ((mImsMgr == null
1969                     || !mImsMgr.isVolteEnabledByPlatform()
1970                     || !mImsMgr.isVolteProvisionedOnDevice()
1971                     || !isImsServiceStateReady(mImsMgr)
1972                     || carrierConfig.getBoolean(
1973                     CarrierConfigManager.KEY_HIDE_ENHANCED_4G_LTE_BOOL))) {
1974                 getPreferenceScreen().removePreference(mButton4glte);
1975             } else {
1976                 mButton4glte.setEnabled(is4gLtePrefEnabled(carrierConfig)
1977                         && hasActiveSubscriptions());
1978                 boolean enh4glteMode = mImsMgr.isEnhanced4gLteModeSettingEnabledByUser()
1979                         && mImsMgr.isNonTtyOrTtyOnVolteEnabled();
1980                 mButton4glte.setChecked(enh4glteMode);
1981             }
1982         }
1983 
updateVideoCallState()1984         private void updateVideoCallState() {
1985             if (mVideoCallingPref == null || mCallingCategory == null) {
1986                 return;
1987             }
1988 
1989             PersistableBundle carrierConfig = mCarrierConfigManager.getConfigForSubId(mSubId);
1990 
1991             if (mImsMgr != null
1992                     && mImsMgr.isVtEnabledByPlatform()
1993                     && mImsMgr.isVtProvisionedOnDevice()
1994                     && isImsServiceStateReady(mImsMgr)
1995                     && (carrierConfig.getBoolean(
1996                         CarrierConfigManager.KEY_IGNORE_DATA_ENABLED_CHANGED_FOR_VIDEO_CALLS)
1997                         || mTelephonyManager.isDataEnabled())) {
1998                 mCallingCategory.addPreference(mVideoCallingPref);
1999                 if (!mButton4glte.isChecked()) {
2000                     mVideoCallingPref.setEnabled(false);
2001                     mVideoCallingPref.setChecked(false);
2002                 } else {
2003                     mVideoCallingPref.setEnabled(mTelephonyManager.getCallState(mSubId)
2004                             == TelephonyManager.CALL_STATE_IDLE && hasActiveSubscriptions());
2005                     mVideoCallingPref.setChecked(mImsMgr.isVtEnabledByUser());
2006                     mVideoCallingPref.setOnPreferenceChangeListener(this);
2007                 }
2008             } else {
2009                 mCallingCategory.removePreference(mVideoCallingPref);
2010             }
2011         }
2012 
updatePreferredNetworkType()2013         private void updatePreferredNetworkType() {
2014             boolean enabled = mTelephonyManager.getCallState(
2015                     mSubId) == TelephonyManager.CALL_STATE_IDLE
2016                     && hasActiveSubscriptions();
2017             Log.i(LOG_TAG, "updatePreferredNetworkType: " + enabled);
2018             // TODO: Disentangle enabled networks vs preferred network mode, it looks like
2019             // both buttons are shown to the user as "Preferred network type" and the options change
2020             // based on what looks like World mode.
2021             if (mButtonEnabledNetworks != null) {
2022                 mButtonEnabledNetworks.setEnabled(enabled);
2023             }
2024             if (mButtonPreferredNetworkMode != null) {
2025                 mButtonPreferredNetworkMode.setEnabled(enabled);
2026             }
2027         }
2028 
updateCallingCategory()2029         private void updateCallingCategory() {
2030             if (mCallingCategory == null) {
2031                 return;
2032             }
2033 
2034             updateWiFiCallState();
2035             updateVideoCallState();
2036 
2037             // If all items in calling category is removed, we remove it from
2038             // the screen. Otherwise we'll see title of the category but nothing
2039             // is in there.
2040             if (mCallingCategory.getPreferenceCount() == 0) {
2041                 getPreferenceScreen().removePreference(mCallingCategory);
2042             } else {
2043                 getPreferenceScreen().addPreference(mCallingCategory);
2044             }
2045         }
2046 
log(String msg)2047         private static void log(String msg) {
2048             Log.d(LOG_TAG, msg);
2049         }
2050 
loge(String msg)2051         private static void loge(String msg) {
2052             Log.e(LOG_TAG, msg);
2053         }
2054 
2055         @Override
onOptionsItemSelected(MenuItem item)2056         public boolean onOptionsItemSelected(MenuItem item) {
2057             final int itemId = item.getItemId();
2058             if (itemId == android.R.id.home) {  // See ActionBar#setDisplayHomeAsUpEnabled()
2059                 // Commenting out "logical up" capability. This is a workaround for issue 5278083.
2060                 //
2061                 // Settings app may not launch this activity via UP_ACTIVITY_CLASS but the other
2062                 // Activity that looks exactly same as UP_ACTIVITY_CLASS ("SubSettings" Activity).
2063                 // At that moment, this Activity launches UP_ACTIVITY_CLASS on top of the Activity.
2064                 // which confuses users.
2065                 // TODO: introduce better mechanism for "up" capability here.
2066             /*Intent intent = new Intent(Intent.ACTION_MAIN);
2067             intent.setClassName(UP_ACTIVITY_PACKAGE, UP_ACTIVITY_CLASS);
2068             intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
2069             startActivity(intent);*/
2070                 getActivity().finish();
2071                 return true;
2072             }
2073             return super.onOptionsItemSelected(item);
2074         }
2075 
isWorldMode()2076         private boolean isWorldMode() {
2077             boolean worldModeOn = false;
2078             final String configString = getResources().getString(R.string.config_world_mode);
2079 
2080             if (!TextUtils.isEmpty(configString)) {
2081                 String[] configArray = configString.split(";");
2082                 // Check if we have World mode configuration set to True only or config is set to True
2083                 // and SIM GID value is also set and matches to the current SIM GID.
2084                 if (configArray != null &&
2085                         ((configArray.length == 1 && configArray[0].equalsIgnoreCase("true"))
2086                                 || (configArray.length == 2 && !TextUtils.isEmpty(configArray[1])
2087                                 && mTelephonyManager != null
2088                                 && configArray[1].equalsIgnoreCase(
2089                                         mTelephonyManager.getGroupIdLevel1())))) {
2090                     worldModeOn = true;
2091                 }
2092             }
2093 
2094             Log.d(LOG_TAG, "isWorldMode=" + worldModeOn);
2095 
2096             return worldModeOn;
2097         }
2098 
controlGsmOptions(boolean enable)2099         private void controlGsmOptions(boolean enable) {
2100             PreferenceScreen prefSet = getPreferenceScreen();
2101             if (prefSet == null) {
2102                 return;
2103             }
2104 
2105             updateGsmUmtsOptions(this, prefSet, mSubId);
2106 
2107             PreferenceCategory networkOperatorCategory =
2108                     (PreferenceCategory) prefSet.findPreference(
2109                             NetworkOperators.CATEGORY_NETWORK_OPERATORS_KEY);
2110             Preference carrierSettings = prefSet.findPreference(BUTTON_CARRIER_SETTINGS_KEY);
2111             if (networkOperatorCategory != null) {
2112                 if (enable) {
2113                     networkOperatorCategory.setEnabled(true);
2114                 } else {
2115                     prefSet.removePreference(networkOperatorCategory);
2116                 }
2117             }
2118             if (carrierSettings != null) {
2119                 prefSet.removePreference(carrierSettings);
2120             }
2121         }
2122 
controlCdmaOptions(boolean enable)2123         private void controlCdmaOptions(boolean enable) {
2124             PreferenceScreen prefSet = getPreferenceScreen();
2125             if (prefSet == null) {
2126                 return;
2127             }
2128             updateCdmaOptions(this, prefSet, mSubId);
2129             CdmaSystemSelectListPreference systemSelect =
2130                     (CdmaSystemSelectListPreference)prefSet.findPreference
2131                             (BUTTON_CDMA_SYSTEM_SELECT_KEY);
2132             systemSelect.setSubscriptionId(mSubId);
2133             if (systemSelect != null) {
2134                 systemSelect.setEnabled(enable);
2135             }
2136         }
2137 
isSupportTdscdma()2138         private boolean isSupportTdscdma() {
2139             if (getResources().getBoolean(R.bool.config_support_tdscdma)) {
2140                 return true;
2141             }
2142 
2143             String operatorNumeric = mTelephonyManager.getServiceState().getOperatorNumeric();
2144             String[] numericArray = getResources().getStringArray(
2145                     R.array.config_support_tdscdma_roaming_on_networks);
2146             if (numericArray.length == 0 || operatorNumeric == null) {
2147                 return false;
2148             }
2149             for (String numeric : numericArray) {
2150                 if (operatorNumeric.equals(numeric)) {
2151                     return true;
2152                 }
2153             }
2154             return false;
2155         }
2156 
2157         /**
2158          * Metrics events related methods. it takes care of all preferences possible in this
2159          * fragment(except a few that log on their own). It doesn't only include preferences in
2160          * network_setting_fragment.xml, but also those defined in GsmUmtsOptions and CdmaOptions.
2161          */
sendMetricsEventPreferenceClicked( PreferenceScreen preferenceScreen, Preference preference)2162         private void sendMetricsEventPreferenceClicked(
2163                 PreferenceScreen preferenceScreen, Preference preference) {
2164             final int category = getMetricsEventCategory(preferenceScreen, preference);
2165             if (category == MetricsEvent.VIEW_UNKNOWN) {
2166                 return;
2167             }
2168 
2169             // Send MetricsEvent on click. It includes preferences other than SwitchPreferences,
2170             // which send MetricsEvent in onPreferenceChange.
2171             // For ListPreferences, we log it here without a value, only indicating it's clicked to
2172             // open the list dialog. When a value is chosen, another MetricsEvent is logged with
2173             // new value in onPreferenceChange.
2174             if (preference == mLteDataServicePref || preference == mDataUsagePref
2175                     || preference == mEuiccSettingsPref || preference == mAdvancedOptions
2176                     || preference == mWiFiCallingPref || preference == mButtonPreferredNetworkMode
2177                     || preference == mButtonEnabledNetworks
2178                     || preference == preferenceScreen.findPreference(BUTTON_CDMA_SYSTEM_SELECT_KEY)
2179                     || preference == preferenceScreen.findPreference(BUTTON_CDMA_SUBSCRIPTION_KEY)
2180                     || preference == preferenceScreen.findPreference(BUTTON_GSM_APN_EXPAND_KEY)
2181                     || preference == preferenceScreen.findPreference(BUTTON_CDMA_APN_EXPAND_KEY)
2182                     || preference == preferenceScreen.findPreference(BUTTON_CARRIER_SETTINGS_KEY)) {
2183                 MetricsLogger.action(getContext(), category);
2184             }
2185         }
2186 
sendMetricsEventPreferenceChanged( PreferenceScreen preferenceScreen, Preference preference, Object newValue)2187         private void sendMetricsEventPreferenceChanged(
2188                 PreferenceScreen preferenceScreen, Preference preference, Object newValue) {
2189             final int category = getMetricsEventCategory(preferenceScreen, preference);
2190             if (category == MetricsEvent.VIEW_UNKNOWN) {
2191                 return;
2192             }
2193 
2194             // MetricsEvent logging with new value, for SwitchPreferences and ListPreferences.
2195             if (preference == mButton4glte || preference == mVideoCallingPref) {
2196                 MetricsLogger.action(getContext(), category, (Boolean) newValue);
2197             } else if (preference == mButtonPreferredNetworkMode
2198                     || preference == mButtonEnabledNetworks
2199                     || preference == preferenceScreen
2200                             .findPreference(BUTTON_CDMA_SYSTEM_SELECT_KEY)
2201                     || preference == preferenceScreen
2202                             .findPreference(BUTTON_CDMA_SUBSCRIPTION_KEY)) {
2203                 // Network select preference sends metrics event in its own listener.
2204                 MetricsLogger.action(getContext(), category, Integer.valueOf((String) newValue));
2205             }
2206         }
2207 
getMetricsEventCategory( PreferenceScreen preferenceScreen, Preference preference)2208         private int getMetricsEventCategory(
2209                 PreferenceScreen preferenceScreen, Preference preference) {
2210 
2211             if (preference == null) {
2212                 return MetricsEvent.VIEW_UNKNOWN;
2213             } else if (preference == mMobileDataPref) {
2214                 return MetricsEvent.ACTION_MOBILE_NETWORK_MOBILE_DATA_TOGGLE;
2215             } else if (preference == mButtonDataRoam) {
2216                 return MetricsEvent.ACTION_MOBILE_NETWORK_DATA_ROAMING_TOGGLE;
2217             } else if (preference == mDataUsagePref) {
2218                 return MetricsEvent.ACTION_MOBILE_NETWORK_DATA_USAGE;
2219             } else if (preference == mLteDataServicePref) {
2220                 return MetricsEvent.ACTION_MOBILE_NETWORK_SET_UP_DATA_SERVICE;
2221             } else if (preference == mAdvancedOptions) {
2222                 return MetricsEvent.ACTION_MOBILE_NETWORK_EXPAND_ADVANCED_FIELDS;
2223             } else if (preference == mButton4glte) {
2224                 return MetricsEvent.ACTION_MOBILE_ENHANCED_4G_LTE_MODE_TOGGLE;
2225             } else if (preference == mButtonPreferredNetworkMode) {
2226                 return MetricsEvent.ACTION_MOBILE_NETWORK_SELECT_PREFERRED_NETWORK;
2227             } else if (preference == mButtonEnabledNetworks) {
2228                 return MetricsEvent.ACTION_MOBILE_NETWORK_SELECT_ENABLED_NETWORK;
2229             } else if (preference == mEuiccSettingsPref) {
2230                 return MetricsEvent.ACTION_MOBILE_NETWORK_EUICC_SETTING;
2231             } else if (preference == mWiFiCallingPref) {
2232                 return MetricsEvent.ACTION_MOBILE_NETWORK_WIFI_CALLING;
2233             } else if (preference == mVideoCallingPref) {
2234                 return MetricsEvent.ACTION_MOBILE_NETWORK_VIDEO_CALLING_TOGGLE;
2235             } else if (preference == preferenceScreen
2236                             .findPreference(NetworkOperators.BUTTON_AUTO_SELECT_KEY)) {
2237                 return MetricsEvent.ACTION_MOBILE_NETWORK_AUTO_SELECT_NETWORK_TOGGLE;
2238             } else if (preference == preferenceScreen
2239                             .findPreference(NetworkOperators.BUTTON_NETWORK_SELECT_KEY)) {
2240                 return MetricsEvent.ACTION_MOBILE_NETWORK_MANUAL_SELECT_NETWORK;
2241             } else if (preference == preferenceScreen
2242                             .findPreference(BUTTON_CDMA_SYSTEM_SELECT_KEY)) {
2243                 return MetricsEvent.ACTION_MOBILE_NETWORK_CDMA_SYSTEM_SELECT;
2244             } else if (preference == preferenceScreen
2245                             .findPreference(BUTTON_CDMA_SUBSCRIPTION_KEY)) {
2246                 return MetricsEvent.ACTION_MOBILE_NETWORK_CDMA_SUBSCRIPTION_SELECT;
2247             } else if (preference == preferenceScreen.findPreference(BUTTON_GSM_APN_EXPAND_KEY)
2248                     || preference == preferenceScreen.findPreference(BUTTON_CDMA_APN_EXPAND_KEY)) {
2249                 return MetricsEvent.ACTION_MOBILE_NETWORK_APN_SETTINGS;
2250             } else if (preference == preferenceScreen.findPreference(BUTTON_CARRIER_SETTINGS_KEY)) {
2251                 return MetricsEvent.ACTION_MOBILE_NETWORK_CARRIER_SETTINGS;
2252             } else {
2253                 return MetricsEvent.VIEW_UNKNOWN;
2254             }
2255         }
2256 
updateGsmUmtsOptions(PreferenceFragment prefFragment, PreferenceScreen prefScreen, final int subId)2257         private void updateGsmUmtsOptions(PreferenceFragment prefFragment,
2258                 PreferenceScreen prefScreen, final int subId) {
2259             // We don't want to re-create GsmUmtsOptions if already exists. Otherwise, the
2260             // preferences inside it will also be re-created which causes unexpected behavior.
2261             // For example, the open dialog gets dismissed or detached after pause / resume.
2262             if (mGsmUmtsOptions == null) {
2263                 mGsmUmtsOptions = new GsmUmtsOptions(prefFragment, prefScreen, subId);
2264             } else {
2265                 mGsmUmtsOptions.update(subId);
2266             }
2267         }
2268 
updateCdmaOptions(PreferenceFragment prefFragment, PreferenceScreen prefScreen, int subId)2269         private void updateCdmaOptions(PreferenceFragment prefFragment, PreferenceScreen prefScreen,
2270                 int subId) {
2271             // We don't want to re-create CdmaOptions if already exists. Otherwise, the preferences
2272             // inside it will also be re-created which causes unexpected behavior. For example,
2273             // the open dialog gets dismissed or detached after pause / resume.
2274             if (mCdmaOptions == null) {
2275                 mCdmaOptions = new CdmaOptions(prefFragment, prefScreen, subId);
2276             } else {
2277                 mCdmaOptions.updateSubscriptionId(subId);
2278             }
2279         }
2280     }
2281 
2282     private static final class SetPreferredNetworkAsyncTask extends AsyncTask<Void, Void, Boolean> {
2283 
2284         private final TelephonyManager mTelephonyManager;
2285         private final int mSubId;
2286         private final int mNetworkType;
2287         private final Message mCallback;
2288 
SetPreferredNetworkAsyncTask( TelephonyManager tm, int subId, int networkType, Message callback)2289         SetPreferredNetworkAsyncTask(
2290                 TelephonyManager tm, int subId, int networkType, Message callback) {
2291             mTelephonyManager = tm;
2292             mSubId = subId;
2293             mNetworkType = networkType;
2294             mCallback = callback;
2295         }
2296 
2297         @Override
doInBackground(Void... voids)2298         protected Boolean doInBackground(Void... voids) {
2299             return mTelephonyManager.setPreferredNetworkType(mSubId, mNetworkType);
2300         }
2301 
2302         @Override
onPostExecute(Boolean isSuccessed)2303         protected void onPostExecute(Boolean isSuccessed) {
2304             mCallback.obj = isSuccessed;
2305             mCallback.sendToTarget();
2306         }
2307     }
2308 }
2309