From cded9d42da7e1d28f1b7f89fc5f54c8b708a2812 Mon Sep 17 00:00:00 2001 From: septs Date: Wed, 6 Nov 2024 10:26:39 +0800 Subject: [PATCH 1/3] refactor: open sim toolkit logical --- app-unpriv/src/main/AndroidManifest.xml | 2 + .../ui/UnprivilegedEuiccManagementFragment.kt | 25 ++---- .../im/angry/openeuicc/util/SIMToolkit.kt | 79 +++++++++++++------ .../src/main/res/values/sim_toolkit.xml | 32 ++++++++ 4 files changed, 98 insertions(+), 40 deletions(-) create mode 100644 app-unpriv/src/main/res/values/sim_toolkit.xml diff --git a/app-unpriv/src/main/AndroidManifest.xml b/app-unpriv/src/main/AndroidManifest.xml index cb1ef5f..8760fb9 100644 --- a/app-unpriv/src/main/AndroidManifest.xml +++ b/app-unpriv/src/main/AndroidManifest.xml @@ -29,5 +29,7 @@ + + \ No newline at end of file diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/ui/UnprivilegedEuiccManagementFragment.kt b/app-unpriv/src/main/java/im/angry/openeuicc/ui/UnprivilegedEuiccManagementFragment.kt index 91c4804..fad03fd 100644 --- a/app-unpriv/src/main/java/im/angry/openeuicc/ui/UnprivilegedEuiccManagementFragment.kt +++ b/app-unpriv/src/main/java/im/angry/openeuicc/ui/UnprivilegedEuiccManagementFragment.kt @@ -1,12 +1,9 @@ package im.angry.openeuicc.ui -import android.util.Log import android.view.Menu import android.view.MenuInflater -import android.view.MenuItem import im.angry.easyeuicc.R import im.angry.openeuicc.util.SIMToolkit -import im.angry.openeuicc.util.isUsb import im.angry.openeuicc.util.newInstanceEuicc import im.angry.openeuicc.util.slotId @@ -19,22 +16,16 @@ class UnprivilegedEuiccManagementFragment : EuiccManagementFragment() { newInstanceEuicc(UnprivilegedEuiccManagementFragment::class.java, slotId, portId) } + private val stk by lazy { + SIMToolkit(requireContext()) + } + override fun onCreateOptionsMenu(menu: Menu, inflater: MenuInflater) { super.onCreateOptionsMenu(menu, inflater) inflater.inflate(R.menu.fragment_sim_toolkit, menu) - menu.findItem(R.id.open_sim_toolkit).isVisible = - SIMToolkit.getComponentName(requireContext(), slotId) != null - } - - override fun onOptionsItemSelected(item: MenuItem): Boolean = - when (item.itemId) { - R.id.open_sim_toolkit -> { - val intent = SIMToolkit.intent(requireContext(), slotId) - Log.d(TAG, "Opening SIM Toolkit for $slotId slot, intent: $intent") - startActivity(intent) - true - } - - else -> super.onOptionsItemSelected(item) + menu.findItem(R.id.open_sim_toolkit).apply { + isVisible = stk.isAvailable(slotId) + intent = stk.intent(slotId) } + } } \ No newline at end of file diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt b/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt index b6aed0f..f2414e6 100644 --- a/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt +++ b/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt @@ -3,36 +3,69 @@ package im.angry.openeuicc.util import android.content.ComponentName import android.content.Context import android.content.Intent -import android.content.pm.PackageManager.NameNotFoundException +import android.content.pm.PackageManager +import androidx.annotation.ArrayRes +import im.angry.easyeuicc.R +import im.angry.openeuicc.core.EuiccChannelManager -object SIMToolkit { - private val slot1activities = arrayOf( - ComponentName("com.android.stk", "com.android.stk.StkMain1"), - ) +class SIMToolkit(private val context: Context) { + private val slotSelection = getComponentNames(R.array.sim_toolkit_slot_selection) - private val slot2activities = arrayOf( - ComponentName("com.android.stk", "com.android.stk.StkMain2"), - ) + private val slots = buildMap { + put(0, getComponentNames(R.array.sim_toolkit_slot_1)) + put(1, getComponentNames(R.array.sim_toolkit_slot_2)) + } - fun getComponentName(context: Context, slotId: Int): ComponentName? { - val components = when (slotId) { - 0 -> slot1activities - 1 -> slot2activities - else -> return null - } - return components.find { + private val packageNames = buildSet { + addAll(slotSelection.map { it.packageName }) + addAll(slots.values.flatten().map { it.packageName }) + } + + private val activities by lazy { + val pm = context.packageManager + packageNames.flatMap { packageName -> try { - context.packageManager.getActivityIcon(it) - true - } catch (_: NameNotFoundException) { - false + val packageInfo = pm.getPackageInfo(packageName, PackageManager.GET_ACTIVITIES) + packageInfo.activities!!.filter { it.exported } + .map { ComponentName(it.packageName, it.name) } + } catch (_: PackageManager.NameNotFoundException) { + emptyList() } } } - fun intent(context: Context, slotId: Int) = Intent(Intent.ACTION_MAIN, null).apply { - flags = Intent.FLAG_ACTIVITY_NEW_TASK - component = getComponentName(context, slotId) - addCategory(Intent.CATEGORY_LAUNCHER) + private val launchIntent by lazy { + val pm = context.packageManager + for (packageName in packageNames) { + try { + return@lazy pm.getLaunchIntentForPackage(packageName) + } catch (_: PackageManager.NameNotFoundException) { + continue + } + } + null + } + + private fun getComponentNames(@ArrayRes id: Int) = context.resources.getStringArray(id) + .mapNotNull(ComponentName::unflattenFromString) + + private fun findComponentName(slotId: Int): ComponentName? { + val components = (slots[slotId] ?: emptySet()) + slotSelection + return components.find(activities::contains) + } + + fun isAvailable(slotId: Int) = when (slotId) { + -1 -> false + EuiccChannelManager.USB_CHANNEL_ID -> false + else -> intent(slotId) != null + } + + fun intent(slotId: Int) = findComponentName(slotId).let { + if (it == null) return@let launchIntent + Intent(Intent.ACTION_MAIN, null).apply { + flags = Intent.FLAG_ACTIVITY_NEW_TASK + component = it + addCategory(Intent.CATEGORY_LAUNCHER) + } } } diff --git a/app-unpriv/src/main/res/values/sim_toolkit.xml b/app-unpriv/src/main/res/values/sim_toolkit.xml new file mode 100644 index 0000000..1f16271 --- /dev/null +++ b/app-unpriv/src/main/res/values/sim_toolkit.xml @@ -0,0 +1,32 @@ + + + + com.android.stk/.StkMain + com.android.stk/.StkMainHide + com.android.stk/.StkListActivity + com.android.stk/.StkLauncherListActivity + + + com.android.stk/.StkMain1 + com.android.stk/.PrimaryStkMain + com.android.stk/.StkLauncherActivity + com.android.stk/.StkLauncherActivity_Chn + com.android.stk/.StkLauncherActivityI + com.android.stk/.OppoStkLauncherActivity1 + com.android.stk/.OplusStkLauncherActivity1 + com.android.stk/.mtk.StkLauncherActivityI + + + com.android.stk/.StkMain2 + com.android.stk/.SecondaryStkMain + com.android.stk/.StkLauncherActivity2 + com.android.stk/.StkLauncherActivityII + com.android.stk/.OppoStkLauncherActivity2 + com.android.stk/.OplusStkLauncherActivity2 + com.android.stk/.mtk.StkLauncherActivityII + com.android.stk1/.StkLauncherActivity + com.android.stk2/.StkLauncherActivity + com.android.stk2/.StkLauncherActivity_Chn + com.android.stk2/.StkLauncherActivity2 + + \ No newline at end of file -- 2.45.3 From 59230b2d15925c7cf544b6c4b4862ce7058edf2f Mon Sep 17 00:00:00 2001 From: septs Date: Thu, 7 Nov 2024 08:53:55 +0800 Subject: [PATCH 2/3] refactor: open sim toolkit logical --- .../im/angry/openeuicc/util/SIMToolkit.kt | 39 +++++++++---------- 1 file changed, 19 insertions(+), 20 deletions(-) diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt b/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt index f2414e6..305f6fb 100644 --- a/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt +++ b/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt @@ -22,35 +22,34 @@ class SIMToolkit(private val context: Context) { } private val activities by lazy { - val pm = context.packageManager - packageNames.flatMap { packageName -> - try { - val packageInfo = pm.getPackageInfo(packageName, PackageManager.GET_ACTIVITIES) - packageInfo.activities!!.filter { it.exported } - .map { ComponentName(it.packageName, it.name) } - } catch (_: PackageManager.NameNotFoundException) { - emptyList() - } - } + packageNames.flatMap(::getActivities).toSet() } private val launchIntent by lazy { + packageNames.firstNotNullOfOrNull(::getLaunchIntent) + } + + private fun getLaunchIntent(packageName: String) = try { val pm = context.packageManager - for (packageName in packageNames) { - try { - return@lazy pm.getLaunchIntentForPackage(packageName) - } catch (_: PackageManager.NameNotFoundException) { - continue - } - } + pm.getLaunchIntentForPackage(packageName) + } catch (_: PackageManager.NameNotFoundException) { null } - private fun getComponentNames(@ArrayRes id: Int) = context.resources.getStringArray(id) - .mapNotNull(ComponentName::unflattenFromString) + private fun getActivities(packageName: String) = try { + val pm = context.packageManager + val packageInfo = pm.getPackageInfo(packageName, PackageManager.GET_ACTIVITIES) + packageInfo.activities!!.filter { it.exported } + .map { ComponentName(it.packageName, it.name) } + } catch (_: PackageManager.NameNotFoundException) { + emptyList() + } + + private fun getComponentNames(@ArrayRes id: Int) = + context.resources.getStringArray(id).mapNotNull(ComponentName::unflattenFromString) private fun findComponentName(slotId: Int): ComponentName? { - val components = (slots[slotId] ?: emptySet()) + slotSelection + val components = slots.getOrDefault(slotId, emptySet()) + slotSelection return components.find(activities::contains) } -- 2.45.3 From 5fc5a3156ac1ddc99c31bf17db832b0ae2809cb2 Mon Sep 17 00:00:00 2001 From: septs Date: Thu, 7 Nov 2024 09:31:49 +0800 Subject: [PATCH 3/3] refactor: open sim toolkit logical --- .../java/im/angry/openeuicc/util/SIMToolkit.kt | 18 ++++++------------ 1 file changed, 6 insertions(+), 12 deletions(-) diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt b/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt index 305f6fb..148e932 100644 --- a/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt +++ b/app-unpriv/src/main/java/im/angry/openeuicc/util/SIMToolkit.kt @@ -21,9 +21,7 @@ class SIMToolkit(private val context: Context) { addAll(slots.values.flatten().map { it.packageName }) } - private val activities by lazy { - packageNames.flatMap(::getActivities).toSet() - } + private val activities = packageNames.flatMap(::getActivities).toSet() private val launchIntent by lazy { packageNames.firstNotNullOfOrNull(::getLaunchIntent) @@ -48,23 +46,19 @@ class SIMToolkit(private val context: Context) { private fun getComponentNames(@ArrayRes id: Int) = context.resources.getStringArray(id).mapNotNull(ComponentName::unflattenFromString) - private fun findComponentName(slotId: Int): ComponentName? { - val components = slots.getOrDefault(slotId, emptySet()) + slotSelection - return components.find(activities::contains) - } - fun isAvailable(slotId: Int) = when (slotId) { -1 -> false EuiccChannelManager.USB_CHANNEL_ID -> false else -> intent(slotId) != null } - fun intent(slotId: Int) = findComponentName(slotId).let { - if (it == null) return@let launchIntent - Intent(Intent.ACTION_MAIN, null).apply { + fun intent(slotId: Int): Intent? { + val components = slots.getOrDefault(slotId, emptySet()) + slotSelection + val intent = Intent(Intent.ACTION_MAIN, null).apply { flags = Intent.FLAG_ACTIVITY_NEW_TASK - component = it + component = components.find(activities::contains) addCategory(Intent.CATEGORY_LAUNCHER) } + return if (intent.component != null) intent else launchIntent } } -- 2.45.3