Make CDMA Call Options UT aware
Introduce the ability for CDMA call options to detect when SS
over UT becomes available or unavailable and integrate the SS
over CDMA fallback carrier config for situations where SS over
UT becomes unavailable.
1) In the case where SS over CDMA is configured, never disable the
supp service settings, because there will always be an avenue to
set the settings.
2) In the case where SS over UT is available, but SS over CDMA is
not, take into account the availability of SS over UT when the
settings are loaded and enable/disable the preference based on that
state. If the device moves from SS over UT capable -> unavailable
during this time, the setting will be disabled. If it happens while
a pending request is already being serviced, the framework will
throw an exception causing the UX to handle this and show an error
as well as gray out the Preference.
3) in the case that neither SS over CDMA or UT is available, just
gray out the settings that require either one be available.
Bug: 191057045
Test: manual
Change-Id: Ie03cce86da911571f3b3b6c3563a2882861818d2
diff --git a/src/com/android/phone/CdmaCallOptions.java b/src/com/android/phone/CdmaCallOptions.java
index 40e3517..6145870 100644
--- a/src/com/android/phone/CdmaCallOptions.java
+++ b/src/com/android/phone/CdmaCallOptions.java
@@ -21,18 +21,37 @@
import android.preference.Preference;
import android.preference.PreferenceScreen;
import android.telephony.CarrierConfigManager;
+import android.telephony.SubscriptionManager;
+import android.telephony.ims.ImsException;
+import android.telephony.ims.ImsManager;
+import android.telephony.ims.ImsMmTelManager;
+import android.telephony.ims.feature.MmTelFeature;
+import android.util.Log;
import android.view.MenuItem;
import com.android.internal.telephony.PhoneConstants;
public class CdmaCallOptions extends TimeConsumingPreferenceActivity {
private static final String LOG_TAG = "CdmaCallOptions";
- private final boolean DBG = (PhoneGlobals.DBG_LEVEL >= 2);
private static final String BUTTON_VP_KEY = "button_voice_privacy_key";
private static final String CALL_FORWARDING_KEY = "call_forwarding_key";
private static final String CALL_WAITING_KEY = "call_waiting_key";
+ private class UtCallback extends ImsMmTelManager.CapabilityCallback {
+ @Override
+ public void onCapabilitiesStatusChanged(MmTelFeature.MmTelCapabilities capabilities) {
+ boolean isUtAvailable = capabilities.isCapable(
+ MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_UT);
+ updatePreferencesEnabled(isUtAvailable);
+ }
+ }
+
+ private Preference mCallForwardingPref;
+ private CdmaCallWaitingPreference mCallWaitingPref;
+ private UtCallback mUtCallback;
+ private ImsMmTelManager mMmTelManager;
+
@Override
protected void onCreate(Bundle icicle) {
super.onCreate(icicle);
@@ -47,33 +66,107 @@
(CdmaVoicePrivacySwitchPreference) findPreference(BUTTON_VP_KEY);
buttonVoicePrivacy.setPhone(subInfoHelper.getPhone());
PersistableBundle carrierConfig;
+ int subId;
if (subInfoHelper.hasSubId()) {
- carrierConfig = PhoneGlobals.getInstance().getCarrierConfigForSubId(
- subInfoHelper.getSubId());
+ subId = subInfoHelper.getSubId();
} else {
- carrierConfig = PhoneGlobals.getInstance().getCarrierConfig();
+ subId = SubscriptionManager.getDefaultSubscriptionId();
}
+ carrierConfig = PhoneGlobals.getInstance().getCarrierConfigForSubId(subId);
if (subInfoHelper.getPhone().getPhoneType() != PhoneConstants.PHONE_TYPE_CDMA
|| carrierConfig.getBoolean(CarrierConfigManager.KEY_VOICE_PRIVACY_DISABLE_UI_BOOL)) {
buttonVoicePrivacy.setEnabled(false);
}
- Preference callForwardingPref = getPreferenceScreen().findPreference(CALL_FORWARDING_KEY);
+ mCallForwardingPref = getPreferenceScreen().findPreference(CALL_FORWARDING_KEY);
if (carrierConfig != null && carrierConfig.getBoolean(
CarrierConfigManager.KEY_CALL_FORWARDING_VISIBILITY_BOOL)) {
- callForwardingPref.setIntent(
+ mCallForwardingPref.setIntent(
subInfoHelper.getIntent(CdmaCallForwardOptions.class));
} else {
- getPreferenceScreen().removePreference(callForwardingPref);
+ getPreferenceScreen().removePreference(mCallForwardingPref);
+ mCallForwardingPref = null;
}
- CdmaCallWaitingPreference callWaitingPref = (CdmaCallWaitingPreference)getPreferenceScreen()
- .findPreference(CALL_WAITING_KEY);
- if (carrierConfig != null && carrierConfig.getBoolean(
+ mCallWaitingPref = (CdmaCallWaitingPreference) getPreferenceScreen()
+ .findPreference(CALL_WAITING_KEY);
+ if (carrierConfig == null || !carrierConfig.getBoolean(
CarrierConfigManager.KEY_ADDITIONAL_SETTINGS_CALL_WAITING_VISIBILITY_BOOL)) {
- callWaitingPref.init(this, subInfoHelper.getPhone());
+ getPreferenceScreen().removePreference(mCallWaitingPref);
+ mCallWaitingPref = null;
+ }
+ // Do not go further if the preferences are removed.
+ if (mCallForwardingPref == null && mCallWaitingPref == null) return;
+
+ boolean isSsOverCdmaEnabled = carrierConfig != null && carrierConfig.getBoolean(
+ CarrierConfigManager.KEY_SUPPORT_SS_OVER_CDMA_BOOL);
+ boolean isSsOverUtEnabled = carrierConfig != null && carrierConfig.getBoolean(
+ CarrierConfigManager.KEY_CARRIER_SUPPORTS_SS_OVER_UT_BOOL);
+
+ if (isSsOverCdmaEnabled && mCallWaitingPref != null) {
+ // If SS over CDMA is enabled, then the preference will always be enabled,
+ // independent of SS over UT status. Initialize it now.
+ mCallWaitingPref.init(this, subInfoHelper.getPhone());
+ return;
+ }
+ // Since SS over UT availability can change, first disable the preferences that rely on it
+ // and only enable it if UT is available.
+ updatePreferencesEnabled(false);
+ if (isSsOverUtEnabled) {
+ // Register a callback to listen to SS over UT state. This will enable the preferences
+ // once the callback notifies settings that UT is enabled.
+ registerMmTelCapsCallback(subId);
} else {
- getPreferenceScreen().removePreference(callWaitingPref);
+ Log.w(LOG_TAG, "SS over UT and CDMA disabled, but preferences are visible.");
+ }
+ }
+
+ @Override
+ public void onStop() {
+ super.onStop();
+ unregisterMmTelCapsCallback();
+ }
+
+ private void unregisterMmTelCapsCallback() {
+ if (mMmTelManager == null || mUtCallback == null) return;
+ mMmTelManager.unregisterMmTelCapabilityCallback(mUtCallback);
+ mUtCallback = null;
+ Log.d(LOG_TAG, "unregisterMmTelCapsCallback: UT availability callback unregistered");
+ }
+
+ private void registerMmTelCapsCallback(int subId) {
+ if (!SubscriptionManager.isValidSubscriptionId(subId)) return;
+ ImsManager imsManager = getSystemService(ImsManager.class);
+ try {
+ if (imsManager != null) {
+ mUtCallback = new UtCallback();
+ mMmTelManager = imsManager.getImsMmTelManager(subId);
+ // Callback will call back with the state as soon as it is available.
+ mMmTelManager.registerMmTelCapabilityCallback(getMainExecutor(), mUtCallback);
+ Log.d(LOG_TAG, "registerMmTelCapsCallback: UT availability callback "
+ + "registered");
+ } else {
+ Log.w(LOG_TAG, "registerMmTelCapsCallback: couldn't get ImsManager, assuming "
+ + "UT is not available: ");
+ updatePreferencesEnabled(false);
+ }
+ } catch (IllegalArgumentException | ImsException e) {
+ Log.w(LOG_TAG, "registerMmTelCapsCallback: couldn't register callback, assuming "
+ + "UT is not available: " + e);
+ updatePreferencesEnabled(false);
+ }
+ }
+
+ private void updatePreferencesEnabled(boolean isEnabled) {
+ Log.d(LOG_TAG, "updatePreferencesEnabled: " + isEnabled);
+ if (mCallForwardingPref != null) mCallForwardingPref.setEnabled(isEnabled);
+
+ if (mCallWaitingPref == null || mCallWaitingPref.isEnabled() == isEnabled) return;
+ mCallWaitingPref.setActionAvailable(isEnabled);
+ if (isEnabled) {
+ SubscriptionInfoHelper subInfoHelper = new SubscriptionInfoHelper(this, getIntent());
+ // kick off the normal process to populate the Call Waiting status.
+ mCallWaitingPref.init(this, subInfoHelper.getPhone());
}
}