forked from PeterCxy/OpenEUICC
Compare commits
3 commits
29d72e8db0
...
e69fcc8d17
Author | SHA1 | Date | |
---|---|---|---|
e69fcc8d17 | |||
dbad335366 | |||
71368b6fc5 |
7 changed files with 46 additions and 26 deletions
|
@ -11,6 +11,7 @@ import androidx.core.app.NotificationManagerCompat
|
|||
import androidx.lifecycle.LifecycleService
|
||||
import androidx.lifecycle.lifecycleScope
|
||||
import im.angry.openeuicc.common.R
|
||||
import im.angry.openeuicc.core.EuiccChannel
|
||||
import im.angry.openeuicc.core.EuiccChannelManager
|
||||
import im.angry.openeuicc.util.*
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
|
@ -446,30 +447,30 @@ class EuiccChannelManagerService : LifecycleService(), OpenEuiccContextMarker {
|
|||
iccid: String,
|
||||
enable: Boolean, // Enable or disable the profile indicated in iccid
|
||||
reconnectTimeoutMillis: Long = 0 // 0 = do not wait for reconnect
|
||||
): ForegroundTaskSubscriberFlow =
|
||||
) =
|
||||
launchForegroundTask(
|
||||
getString(R.string.task_profile_switch),
|
||||
getString(R.string.task_profile_switch_failure),
|
||||
R.drawable.ic_task_switch
|
||||
) {
|
||||
euiccChannelManager.beginTrackedOperation(slotId, portId) {
|
||||
val (res, refreshed) = euiccChannelManager.withEuiccChannel(
|
||||
slotId,
|
||||
portId
|
||||
) { channel ->
|
||||
if (!channel.lpa.switchProfile(iccid, enable, refresh = true)) {
|
||||
// Sometimes, we *can* enable or disable the profile, but we cannot
|
||||
// send the refresh command to the modem because the profile somehow
|
||||
// makes the modem "busy". In this case, we can still switch by setting
|
||||
// refresh to false, but then the switch cannot take effect until the
|
||||
// user resets the modem manually by toggling airplane mode or rebooting.
|
||||
Pair(channel.lpa.switchProfile(iccid, enable, refresh = false), false)
|
||||
} else {
|
||||
Pair(true, true)
|
||||
}
|
||||
}
|
||||
suspend fun onSwitch(channel: EuiccChannel): Pair<Boolean, Boolean> {
|
||||
val refresh = preferenceRepository.refreshAfterSwitchFlow.first()
|
||||
val response = channel.lpa.switchProfile(iccid, enable, refresh)
|
||||
if (response || !refresh) return Pair(response, refresh)
|
||||
// refresh failed, but refresh was requested
|
||||
// Sometimes, we *can* enable or disable the profile, but we cannot
|
||||
// send the refresh command to the modem because the profile somehow
|
||||
// makes the modem "busy". In this case, we can still switch by setting
|
||||
// refresh to false, but then the switch cannot take effect until the
|
||||
// user resets the modem manually by toggling airplane mode or rebooting.
|
||||
return Pair(channel.lpa.switchProfile(iccid, enable, refresh = false), false)
|
||||
}
|
||||
|
||||
if (!res) {
|
||||
euiccChannelManager.beginTrackedOperation(slotId, portId) {
|
||||
val (response, refreshed) =
|
||||
euiccChannelManager.withEuiccChannel(slotId, portId, ::onSwitch)
|
||||
|
||||
if (!response) {
|
||||
throw RuntimeException("Could not switch profile")
|
||||
}
|
||||
|
||||
|
|
|
@ -122,7 +122,7 @@ open class SettingsFragment: PreferenceFragmentCompat() {
|
|||
return true
|
||||
}
|
||||
|
||||
private fun CheckBoxPreference.bindBooleanFlow(flow: PreferenceFlowWrapper<Boolean>) {
|
||||
protected fun CheckBoxPreference.bindBooleanFlow(flow: PreferenceFlowWrapper<Boolean>) {
|
||||
lifecycleScope.launch {
|
||||
flow.collect { isChecked = it }
|
||||
}
|
||||
|
|
|
@ -26,6 +26,7 @@ internal object PreferenceKeys {
|
|||
val NOTIFICATION_SWITCH = booleanPreferencesKey("notification_switch")
|
||||
|
||||
// ---- Advanced ----
|
||||
val REFRESH_AFTER_SWITCH = booleanPreferencesKey("refresh_after_switch")
|
||||
val DISABLE_SAFEGUARD_REMOVABLE_ESIM = booleanPreferencesKey("disable_safeguard_removable_esim")
|
||||
val VERBOSE_LOGGING = booleanPreferencesKey("verbose_logging")
|
||||
|
||||
|
@ -47,6 +48,7 @@ class PreferenceRepository(private val context: Context) {
|
|||
val verboseLoggingFlow = bindFlow(PreferenceKeys.VERBOSE_LOGGING, false)
|
||||
|
||||
// ---- Developer Options ----
|
||||
val refreshAfterSwitchFlow = bindFlow(PreferenceKeys.REFRESH_AFTER_SWITCH, true)
|
||||
val developerOptionsEnabledFlow = bindFlow(PreferenceKeys.DEVELOPER_OPTIONS_ENABLED, false)
|
||||
val unfilteredProfileListFlow = bindFlow(PreferenceKeys.UNFILTERED_PROFILE_LIST, false)
|
||||
val ignoreTLSCertificateFlow = bindFlow(PreferenceKeys.IGNORE_TLS_CERTIFICATE, false)
|
||||
|
@ -58,15 +60,12 @@ class PreferenceRepository(private val context: Context) {
|
|||
class PreferenceFlowWrapper<T> private constructor(
|
||||
private val context: Context,
|
||||
private val key: Preferences.Key<T>,
|
||||
inner: Flow<T>
|
||||
inner: Flow<T>,
|
||||
) : Flow<T> by inner {
|
||||
internal constructor(context: Context, key: Preferences.Key<T>, defaultValue: T) : this(
|
||||
context,
|
||||
key,
|
||||
context.dataStore.data.map { it[key] ?: defaultValue }
|
||||
)
|
||||
internal constructor(context: Context, key: Preferences.Key<T>, defaultValue: T) :
|
||||
this(context, key, context.dataStore.data.map { it[key] ?: defaultValue })
|
||||
|
||||
suspend fun updatePreference(value: T) {
|
||||
context.dataStore.edit { it[key] = value }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -162,6 +162,8 @@
|
|||
<string name="pref_notifications_switch">Switching</string>
|
||||
<string name="pref_notifications_switch_desc">Send notifications for <i>switching</i> profiles\nNote that this type of notification is unreliable.</string>
|
||||
<string name="pref_advanced">Advanced</string>
|
||||
<string name="pref_advanced_refresh_after_switch">Refresh status after switching</string>
|
||||
<string name="pref_advanced_refresh_after_switch_desc">If crash after switch, Please trying disable the function</string>
|
||||
<string name="pref_advanced_disable_safeguard_removable_esim">Allow Disabling / Deleting Active Profile</string>
|
||||
<string name="pref_advanced_disable_safeguard_removable_esim_desc">By default, this app prevents you from disabling the active profile on a removable eSIM inserted in the device, because doing so may <i>sometimes</i> render it inaccessible.\nCheck this box to <i>remove</i> this safeguard.</string>
|
||||
<string name="pref_advanced_verbose_logging">Verbose Logging</string>
|
||||
|
|
|
@ -60,12 +60,14 @@
|
|||
<CheckBoxPreference
|
||||
app:iconSpaceReserved="false"
|
||||
app:key="pref_developer_unfiltered_profile_list"
|
||||
app:order="2"
|
||||
app:summary="@string/pref_developer_unfiltered_profile_list_desc"
|
||||
app:title="@string/pref_developer_unfiltered_profile_list" />
|
||||
|
||||
<CheckBoxPreference
|
||||
app:iconSpaceReserved="false"
|
||||
app:key="pref_developer_ignore_tls_certificate"
|
||||
app:order="3"
|
||||
app:summary="@string/pref_developer_ignore_tls_certificate_desc"
|
||||
app:title="@string/pref_developer_ignore_tls_certificate" />
|
||||
|
||||
|
|
|
@ -6,9 +6,11 @@ import android.content.pm.PackageManager
|
|||
import android.os.Build
|
||||
import android.os.Bundle
|
||||
import android.widget.Toast
|
||||
import androidx.preference.CheckBoxPreference
|
||||
import androidx.preference.Preference
|
||||
import im.angry.easyeuicc.R
|
||||
import im.angry.openeuicc.util.encodeHex
|
||||
import im.angry.openeuicc.util.preferenceRepository
|
||||
import java.security.MessageDigest
|
||||
|
||||
class UnprivilegedSettingsFragment : SettingsFragment() {
|
||||
|
@ -29,8 +31,12 @@ class UnprivilegedSettingsFragment : SettingsFragment() {
|
|||
override fun onCreatePreferences(savedInstanceState: Bundle?, rootKey: String?) {
|
||||
super.onCreatePreferences(savedInstanceState, rootKey)
|
||||
addPreferencesFromResource(R.xml.pref_unprivileged_settings)
|
||||
mergePreferenceOverlay("pref_developer_overlay", "pref_developer")
|
||||
mergePreferenceOverlay("pref_info_overlay", "pref_info")
|
||||
|
||||
requirePreference<CheckBoxPreference>("pref_developer_refreshed_after_switch")
|
||||
.bindBooleanFlow(preferenceRepository.refreshAfterSwitchFlow)
|
||||
|
||||
requirePreference<Preference>("pref_info_ara_m").apply {
|
||||
summary = firstSigner.encodeHex()
|
||||
setOnPreferenceClickListener {
|
||||
|
|
|
@ -1,5 +1,15 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<PreferenceScreen xmlns:app="http://schemas.android.com/apk/res-auto">
|
||||
<PreferenceCategory
|
||||
app:isPreferenceVisible="false"
|
||||
app:key="pref_developer_overlay">
|
||||
<CheckBoxPreference
|
||||
app:iconSpaceReserved="false"
|
||||
app:key="pref_developer_refreshed_after_switch"
|
||||
app:order="1"
|
||||
app:summary="@string/pref_advanced_refresh_after_switch_desc"
|
||||
app:title="@string/pref_advanced_refresh_after_switch" />
|
||||
</PreferenceCategory>
|
||||
<PreferenceCategory
|
||||
app:isPreferenceVisible="false"
|
||||
app:key="pref_info_overlay">
|
||||
|
|
Loading…
Add table
Reference in a new issue