[Catalyst] Fix UI flicker when toggle Airplane mode
The UI flicker is because preference change is notified twice after onActivityResult calls setBoolean: 1) Catalyst framework registers a common listener on each preference's storage to update UI when preference value is changed. 2) The PhoneStateListener in AirplaneModeStorage. Remove the second listener fixes the issue. NO_IFTTT=Catalyst only Fix: 395774878 Flag: com.android.settings.flags.catalyst Test: manual Change-Id: I9f93faf1da87d52a82d9019361b17b4b500d79fe
This commit is contained in:
@@ -21,11 +21,9 @@ import android.app.settings.SettingsEnums.ACTION_AIRPLANE_TOGGLE
|
|||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
import android.content.pm.PackageManager
|
import android.content.pm.PackageManager
|
||||||
import android.os.Looper
|
|
||||||
import android.os.UserHandle
|
import android.os.UserHandle
|
||||||
import android.os.UserManager
|
import android.os.UserManager
|
||||||
import android.provider.Settings
|
import android.provider.Settings
|
||||||
import android.telephony.PhoneStateListener
|
|
||||||
import android.telephony.TelephonyManager
|
import android.telephony.TelephonyManager
|
||||||
import androidx.annotation.DrawableRes
|
import androidx.annotation.DrawableRes
|
||||||
import androidx.preference.Preference
|
import androidx.preference.Preference
|
||||||
@@ -37,12 +35,11 @@ import com.android.settings.metrics.PreferenceActionMetricsProvider
|
|||||||
import com.android.settings.network.SatelliteRepository.Companion.isSatelliteOn
|
import com.android.settings.network.SatelliteRepository.Companion.isSatelliteOn
|
||||||
import com.android.settings.restriction.PreferenceRestrictionMixin
|
import com.android.settings.restriction.PreferenceRestrictionMixin
|
||||||
import com.android.settingslib.RestrictedSwitchPreference
|
import com.android.settingslib.RestrictedSwitchPreference
|
||||||
import com.android.settingslib.datastore.AbstractKeyedDataObservable
|
|
||||||
import com.android.settingslib.datastore.KeyValueStore
|
import com.android.settingslib.datastore.KeyValueStore
|
||||||
|
import com.android.settingslib.datastore.KeyedObservableDelegate
|
||||||
import com.android.settingslib.datastore.SettingsGlobalStore
|
import com.android.settingslib.datastore.SettingsGlobalStore
|
||||||
import com.android.settingslib.datastore.SettingsStore
|
import com.android.settingslib.datastore.SettingsStore
|
||||||
import com.android.settingslib.metadata.PreferenceAvailabilityProvider
|
import com.android.settingslib.metadata.PreferenceAvailabilityProvider
|
||||||
import com.android.settingslib.metadata.PreferenceChangeReason
|
|
||||||
import com.android.settingslib.metadata.PreferenceLifecycleContext
|
import com.android.settingslib.metadata.PreferenceLifecycleContext
|
||||||
import com.android.settingslib.metadata.PreferenceLifecycleProvider
|
import com.android.settingslib.metadata.PreferenceLifecycleProvider
|
||||||
import com.android.settingslib.metadata.ReadWritePermit
|
import com.android.settingslib.metadata.ReadWritePermit
|
||||||
@@ -78,12 +75,7 @@ class AirplaneModePreference :
|
|||||||
override fun getReadPermit(context: Context, callingPid: Int, callingUid: Int) =
|
override fun getReadPermit(context: Context, callingPid: Int, callingUid: Int) =
|
||||||
ReadWritePermit.ALLOW
|
ReadWritePermit.ALLOW
|
||||||
|
|
||||||
override fun getWritePermit(
|
override fun getWritePermit(context: Context, callingPid: Int, callingUid: Int) =
|
||||||
context: Context,
|
|
||||||
value: Boolean?,
|
|
||||||
callingPid: Int,
|
|
||||||
callingUid: Int,
|
|
||||||
) =
|
|
||||||
when {
|
when {
|
||||||
isSatelliteOn(context) || isInEcmMode(context) -> ReadWritePermit.DISALLOW
|
isSatelliteOn(context) || isInEcmMode(context) -> ReadWritePermit.DISALLOW
|
||||||
else -> ReadWritePermit.ALLOW
|
else -> ReadWritePermit.ALLOW
|
||||||
@@ -95,19 +87,15 @@ class AirplaneModePreference :
|
|||||||
override val preferenceActionMetrics: Int
|
override val preferenceActionMetrics: Int
|
||||||
get() = ACTION_AIRPLANE_TOGGLE
|
get() = ACTION_AIRPLANE_TOGGLE
|
||||||
|
|
||||||
override fun storage(context: Context): KeyValueStore =
|
override fun storage(context: Context): KeyValueStore = AirplaneModeStorage(context)
|
||||||
AirplaneModeStorage(context, SettingsGlobalStore.get(context))
|
|
||||||
|
|
||||||
@Suppress("DEPRECATION", "MissingPermission", "UNCHECKED_CAST")
|
@Suppress("UNCHECKED_CAST")
|
||||||
private class AirplaneModeStorage(
|
private class AirplaneModeStorage(
|
||||||
private val context: Context,
|
private val context: Context,
|
||||||
private val settingsStore: SettingsStore,
|
private val settingsStore: SettingsStore = SettingsGlobalStore.get(context),
|
||||||
) : AbstractKeyedDataObservable<String>(), KeyValueStore {
|
) : KeyedObservableDelegate<String>(settingsStore), KeyValueStore {
|
||||||
private var phoneStateListener: PhoneStateListener? = null
|
|
||||||
|
|
||||||
override fun contains(key: String) =
|
override fun contains(key: String) = settingsStore.contains(KEY)
|
||||||
settingsStore.contains(KEY) &&
|
|
||||||
context.getSystemService(TelephonyManager::class.java) != null
|
|
||||||
|
|
||||||
override fun <T : Any> getDefaultValue(key: String, valueType: Class<T>) =
|
override fun <T : Any> getDefaultValue(key: String, valueType: Class<T>) =
|
||||||
DEFAULT_VALUE as T
|
DEFAULT_VALUE as T
|
||||||
@@ -116,31 +104,12 @@ class AirplaneModePreference :
|
|||||||
(settingsStore.getBoolean(key) ?: DEFAULT_VALUE) as T
|
(settingsStore.getBoolean(key) ?: DEFAULT_VALUE) as T
|
||||||
|
|
||||||
override fun <T : Any> setValue(key: String, valueType: Class<T>, value: T?) {
|
override fun <T : Any> setValue(key: String, valueType: Class<T>, value: T?) {
|
||||||
if (value !is Boolean) return
|
settingsStore.setValue(key, valueType, value)
|
||||||
settingsStore.setBoolean(key, value)
|
|
||||||
|
|
||||||
val intent = Intent(Intent.ACTION_AIRPLANE_MODE_CHANGED)
|
val intent = Intent(Intent.ACTION_AIRPLANE_MODE_CHANGED)
|
||||||
intent.putExtra("state", value)
|
intent.putExtra("state", getBoolean(KEY)!!)
|
||||||
context.sendBroadcastAsUser(intent, UserHandle.ALL)
|
context.sendBroadcastAsUser(intent, UserHandle.ALL)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onFirstObserverAdded() {
|
|
||||||
context.getSystemService(TelephonyManager::class.java)?.let {
|
|
||||||
phoneStateListener =
|
|
||||||
object : PhoneStateListener(Looper.getMainLooper()) {
|
|
||||||
override fun onRadioPowerStateChanged(state: Int) {
|
|
||||||
notifyChange(KEY, PreferenceChangeReason.VALUE)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
it.listen(phoneStateListener, PhoneStateListener.LISTEN_RADIO_POWER_STATE_CHANGED)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onLastObserverRemoved() {
|
|
||||||
context
|
|
||||||
.getSystemService(TelephonyManager::class.java)
|
|
||||||
?.listen(phoneStateListener, PhoneStateListener.LISTEN_NONE)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCreate(context: PreferenceLifecycleContext) {
|
override fun onCreate(context: PreferenceLifecycleContext) {
|
||||||
@@ -198,7 +167,7 @@ class AirplaneModePreference :
|
|||||||
const val DEFAULT_VALUE = false
|
const val DEFAULT_VALUE = false
|
||||||
const val REQUEST_CODE_EXIT_ECM = 1
|
const val REQUEST_CODE_EXIT_ECM = 1
|
||||||
|
|
||||||
fun Context.isAirplaneModeOn() = SettingsGlobalStore.get(this).getBoolean(KEY) == true
|
fun Context.isAirplaneModeOn() = AirplaneModeStorage(this).getBoolean(KEY) == true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// LINT.ThenChange(AirplaneModePreferenceController.java)
|
// LINT.ThenChange(AirplaneModePreferenceController.java)
|
||||||
|
Reference in New Issue
Block a user