Async load eid in SimEidPreferenceController
Avoid data loading in getAvailabilityStatus() to prevent ANR, override
updateNonIndexableKeys() for search availability.
Fix: 304560734
Test: manual - on "About phone" page
Change-Id: I9994abf3787f5db0edc71ff48d08e549a4b70bf7
diff --git a/res/xml/my_device_info.xml b/res/xml/my_device_info.xml
index 9325969..29c3c62 100644
--- a/res/xml/my_device_info.xml
+++ b/res/xml/my_device_info.xml
@@ -114,7 +114,7 @@
settings:controller="com.android.settings.deviceinfo.HardwareInfoPreferenceController"/>
<!-- EID -->
- <com.android.settings.network.telephony.TelephonyPreferenceDialog
+ <com.android.settingslib.CustomDialogPreferenceCompat
android:key="eid_info"
android:order="31"
android:title="@string/status_eid"
diff --git a/src/com/android/settings/deviceinfo/simstatus/SimEidPreferenceController.kt b/src/com/android/settings/deviceinfo/simstatus/SimEidPreferenceController.kt
index 4d1b90b..5a3ff49 100644
--- a/src/com/android/settings/deviceinfo/simstatus/SimEidPreferenceController.kt
+++ b/src/com/android/settings/deviceinfo/simstatus/SimEidPreferenceController.kt
@@ -21,16 +21,24 @@
import android.view.WindowManager
import android.widget.ImageView
import android.widget.TextView
+import androidx.lifecycle.Lifecycle
+import androidx.lifecycle.LifecycleOwner
+import androidx.lifecycle.lifecycleScope
+import androidx.lifecycle.repeatOnLifecycle
import androidx.preference.Preference
import androidx.preference.PreferenceScreen
import com.android.settings.R
import com.android.settings.core.BasePreferenceController
import com.android.settings.deviceinfo.PhoneNumberUtil
import com.android.settings.network.SubscriptionUtil
-import com.android.settings.network.telephony.TelephonyPreferenceDialog
+import com.android.settingslib.CustomDialogPreferenceCompat
import com.android.settingslib.Utils
import com.android.settingslib.qrcode.QrCodeGenerator
import com.android.settingslib.spaprivileged.framework.common.userManager
+import kotlinx.coroutines.CoroutineScope
+import kotlinx.coroutines.Dispatchers
+import kotlinx.coroutines.launch
+import kotlinx.coroutines.withContext
/**
* This is to show a preference regarding EID of SIM card.
@@ -41,7 +49,8 @@
BasePreferenceController(context, preferenceKey) {
private var slotSimStatus: SlotSimStatus? = null
private var eidStatus: EidStatus? = null
- private lateinit var preference: TelephonyPreferenceDialog
+ private lateinit var preference: CustomDialogPreferenceCompat
+ private var coroutineScope: CoroutineScope? = null
private lateinit var eid: String
fun init(slotSimStatus: SlotSimStatus?, eidStatus: EidStatus?) {
@@ -49,21 +58,51 @@
this.eidStatus = eidStatus
}
- override fun getAvailabilityStatus(): Int {
- if (!SubscriptionUtil.isSimHardwareVisible(mContext)) return UNSUPPORTED_ON_DEVICE
- eid = eidStatus?.eid ?: ""
- val isAvailable = mContext.userManager.isAdminUser &&
- !Utils.isWifiOnly(mContext) &&
- eid.isNotEmpty()
- return if (isAvailable) AVAILABLE else CONDITIONALLY_UNAVAILABLE
- }
+ /**
+ * Returns available here, but UI availability is retrieved asynchronously later.
+ *
+ * Check [updateNonIndexableKeys] for search availability.
+ */
+ override fun getAvailabilityStatus() = AVAILABLE
override fun displayPreference(screen: PreferenceScreen) {
super.displayPreference(screen)
preference = screen.findPreference(preferenceKey)!!
- val title = getTitle()
- preference.title = title
- preference.dialogTitle = title
+ }
+
+ override fun onViewCreated(viewLifecycleOwner: LifecycleOwner) {
+ coroutineScope = viewLifecycleOwner.lifecycleScope
+ coroutineScope?.launch {
+ viewLifecycleOwner.repeatOnLifecycle(Lifecycle.State.STARTED) {
+ update()
+ }
+ }
+ }
+
+ private suspend fun update() {
+ val isAvailable = withContext(Dispatchers.Default) {
+ getIsAvailableAndUpdateEid()
+ }
+ preference.isVisible = isAvailable
+ if (isAvailable) {
+ val title = withContext(Dispatchers.Default) {
+ getTitle()
+ }
+ preference.title = title
+ preference.dialogTitle = title
+ updateDialog()
+ }
+ }
+
+ private fun getIsAvailableAndUpdateEid(): Boolean {
+ if (!SubscriptionUtil.isSimHardwareVisible(mContext) ||
+ !mContext.userManager.isAdminUser ||
+ Utils.isWifiOnly(mContext)
+ ) {
+ return false
+ }
+ eid = eidStatus?.eid ?: ""
+ return eid.isNotEmpty()
}
/** Constructs title string. */
@@ -82,13 +121,7 @@
return mContext.getString(R.string.status_eid)
}
- override fun updateState(preference: Preference?) {
- super.updateState(preference)
-
- updateDialog()
- }
-
- private fun updateDialog() {
+ private suspend fun updateDialog() {
val dialog = preference.dialog ?: return
dialog.window?.setFlags(
WindowManager.LayoutParams.FLAG_SECURE,
@@ -106,11 +139,17 @@
}
override fun handlePreferenceTreeClick(preference: Preference): Boolean {
- if (preference.key == preferenceKey) {
- this.preference.setOnShowListener { updateDialog() }
- return true
+ if (preference.key != preferenceKey) return false
+ this.preference.setOnShowListener {
+ coroutineScope?.launch { updateDialog() }
}
- return super.handlePreferenceTreeClick(preference)
+ return true
+ }
+
+ override fun updateNonIndexableKeys(keys: MutableList<String>) {
+ if (!getIsAvailableAndUpdateEid()) {
+ keys.add(preferenceKey)
+ }
}
companion object {
@@ -122,11 +161,13 @@
* @param eid is the EID string
* @return a Bitmap of QR code
*/
- private fun getEidQrCode(eid: String): Bitmap? = try {
- QrCodeGenerator.encodeQrCode(eid, QR_CODE_SIZE)
- } catch (exception: Exception) {
- Log.w(TAG, "Error when creating QR code width $QR_CODE_SIZE", exception)
- null
+ private suspend fun getEidQrCode(eid: String): Bitmap? = withContext(Dispatchers.Default) {
+ try {
+ QrCodeGenerator.encodeQrCode(contents = eid, size = QR_CODE_SIZE)
+ } catch (exception: Exception) {
+ Log.w(TAG, "Error when creating QR code width $QR_CODE_SIZE", exception)
+ null
+ }
}
}
}
diff --git a/src/com/android/settings/network/telephony/TelephonyPreferenceDialog.java b/src/com/android/settings/network/telephony/TelephonyPreferenceDialog.java
deleted file mode 100644
index 7dbef0c..0000000
--- a/src/com/android/settings/network/telephony/TelephonyPreferenceDialog.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright (C) 2022 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.settings.network.telephony;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import com.android.settingslib.CustomDialogPreferenceCompat;
-
-/**
- * This is DialogPreference for supporting connectivity features.
- */
-public class TelephonyPreferenceDialog extends CustomDialogPreferenceCompat {
-
- public TelephonyPreferenceDialog(Context context, AttributeSet attrs, int defStyleAttr,
- int defStyleRes) {
- super(context, attrs, defStyleAttr, defStyleRes);
- }
-
- public TelephonyPreferenceDialog(Context context, AttributeSet attrs, int defStyleAttr) {
- super(context, attrs, defStyleAttr);
- }
-
- public TelephonyPreferenceDialog(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public TelephonyPreferenceDialog(Context context) {
- super(context);
- }
-}