diff --git a/app-common/src/main/java/im/angry/openeuicc/core/DefaultEuiccChannelFactory.kt b/app-common/src/main/java/im/angry/openeuicc/core/DefaultEuiccChannelFactory.kt index 15e01912..c741f497 100644 --- a/app-common/src/main/java/im/angry/openeuicc/core/DefaultEuiccChannelFactory.kt +++ b/app-common/src/main/java/im/angry/openeuicc/core/DefaultEuiccChannelFactory.kt @@ -24,7 +24,7 @@ open class DefaultEuiccChannelFactory(protected val context: Context) : EuiccCha Log.i(DefaultEuiccChannelManager.TAG, "Trying OMAPI for physical slot ${port.card.physicalSlotIndex}") try { - return OmapiChannel(seService!!, port) + return EuiccChannel(port, OmapiApduInterface(seService!!, port)) } catch (e: IllegalArgumentException) { // Failed Log.w( diff --git a/app-common/src/main/java/im/angry/openeuicc/core/EuiccChannel.kt b/app-common/src/main/java/im/angry/openeuicc/core/EuiccChannel.kt index 003c0ccf..35cf0ad0 100644 --- a/app-common/src/main/java/im/angry/openeuicc/core/EuiccChannel.kt +++ b/app-common/src/main/java/im/angry/openeuicc/core/EuiccChannel.kt @@ -1,16 +1,21 @@ package im.angry.openeuicc.core import im.angry.openeuicc.util.* +import net.typeblog.lpac_jni.ApduInterface import net.typeblog.lpac_jni.LocalProfileAssistant +import net.typeblog.lpac_jni.impl.HttpInterfaceImpl +import net.typeblog.lpac_jni.impl.LocalProfileAssistantImpl -abstract class EuiccChannel( - val port: UiccPortInfoCompat +class EuiccChannel( + val port: UiccPortInfoCompat, + apduInterface: ApduInterface, ) { val slotId = port.card.physicalSlotIndex // PHYSICAL slot val logicalSlotId = port.logicalSlotIndex val portId = port.portIndex - abstract val lpa: LocalProfileAssistant + val lpa: LocalProfileAssistant = LocalProfileAssistantImpl(apduInterface, HttpInterfaceImpl()) + val valid: Boolean get() = lpa.valid diff --git a/app-common/src/main/java/im/angry/openeuicc/core/OmapiApduInterface.kt b/app-common/src/main/java/im/angry/openeuicc/core/OmapiApduInterface.kt index 1349f3c8..3d3bfe11 100644 --- a/app-common/src/main/java/im/angry/openeuicc/core/OmapiApduInterface.kt +++ b/app-common/src/main/java/im/angry/openeuicc/core/OmapiApduInterface.kt @@ -5,9 +5,6 @@ import android.se.omapi.SEService import android.se.omapi.Session import im.angry.openeuicc.util.* import net.typeblog.lpac_jni.ApduInterface -import net.typeblog.lpac_jni.LocalProfileAssistant -import net.typeblog.lpac_jni.impl.HttpInterfaceImpl -import net.typeblog.lpac_jni.impl.LocalProfileAssistantImpl class OmapiApduInterface( private val service: SEService, @@ -47,13 +44,4 @@ class OmapiApduInterface( return lastChannel.transmit(tx) } -} - -class OmapiChannel( - service: SEService, - port: UiccPortInfoCompat, -) : EuiccChannel(port) { - override val lpa: LocalProfileAssistant = LocalProfileAssistantImpl( - OmapiApduInterface(service, port), - HttpInterfaceImpl()) -} +} \ No newline at end of file diff --git a/app-common/src/main/java/im/angry/openeuicc/di/DefaultUiComponentFactory.kt b/app-common/src/main/java/im/angry/openeuicc/di/DefaultUiComponentFactory.kt index 86af0076..32550d63 100644 --- a/app-common/src/main/java/im/angry/openeuicc/di/DefaultUiComponentFactory.kt +++ b/app-common/src/main/java/im/angry/openeuicc/di/DefaultUiComponentFactory.kt @@ -1,9 +1,13 @@ package im.angry.openeuicc.di +import androidx.fragment.app.Fragment import im.angry.openeuicc.core.EuiccChannel import im.angry.openeuicc.ui.EuiccManagementFragment +import im.angry.openeuicc.ui.NoEuiccPlaceholderFragment open class DefaultUiComponentFactory : UiComponentFactory { override fun createEuiccManagementFragment(channel: EuiccChannel): EuiccManagementFragment = EuiccManagementFragment.newInstance(channel.slotId, channel.portId) + + override fun createNoEuiccPlaceholderFragment(): Fragment = NoEuiccPlaceholderFragment() } \ No newline at end of file diff --git a/app-common/src/main/java/im/angry/openeuicc/di/UiComponentFactory.kt b/app-common/src/main/java/im/angry/openeuicc/di/UiComponentFactory.kt index d311876e..4e09a709 100644 --- a/app-common/src/main/java/im/angry/openeuicc/di/UiComponentFactory.kt +++ b/app-common/src/main/java/im/angry/openeuicc/di/UiComponentFactory.kt @@ -1,8 +1,10 @@ package im.angry.openeuicc.di +import androidx.fragment.app.Fragment import im.angry.openeuicc.core.EuiccChannel import im.angry.openeuicc.ui.EuiccManagementFragment interface UiComponentFactory { fun createEuiccManagementFragment(channel: EuiccChannel): EuiccManagementFragment + fun createNoEuiccPlaceholderFragment(): Fragment } \ No newline at end of file diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/EuiccManagementFragment.kt b/app-common/src/main/java/im/angry/openeuicc/ui/EuiccManagementFragment.kt index d2e7caa2..7564cc88 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/EuiccManagementFragment.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/EuiccManagementFragment.kt @@ -58,9 +58,9 @@ open class EuiccManagementFragment : Fragment(), EuiccProfilesChangedListener, ): View { val view = inflater.inflate(R.layout.fragment_euicc, container, false) - swipeRefresh = view.findViewById(R.id.swipe_refresh) - fab = view.findViewById(R.id.fab) - profileList = view.findViewById(R.id.profile_list) + swipeRefresh = view.requireViewById(R.id.swipe_refresh) + fab = view.requireViewById(R.id.fab) + profileList = view.requireViewById(R.id.profile_list) return view } @@ -191,11 +191,11 @@ open class EuiccManagementFragment : Fragment(), EuiccProfilesChangedListener, } inner class ProfileViewHolder(private val root: View) : ViewHolder(root) { - private val iccid: TextView = root.findViewById(R.id.iccid) - private val name: TextView = root.findViewById(R.id.name) - private val state: TextView = root.findViewById(R.id.state) - private val provider: TextView = root.findViewById(R.id.provider) - private val profileMenu: ImageButton = root.findViewById(R.id.profile_menu) + private val iccid: TextView = root.requireViewById(R.id.iccid) + private val name: TextView = root.requireViewById(R.id.name) + private val state: TextView = root.requireViewById(R.id.state) + private val provider: TextView = root.requireViewById(R.id.provider) + private val profileMenu: ImageButton = root.requireViewById(R.id.profile_menu) init { iccid.setOnClickListener { diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/LogsActivity.kt b/app-common/src/main/java/im/angry/openeuicc/ui/LogsActivity.kt index 70f6992b..2b364683 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/LogsActivity.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/LogsActivity.kt @@ -39,12 +39,12 @@ class LogsActivity : AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_logs) - setSupportActionBar(findViewById(R.id.toolbar)) + setSupportActionBar(requireViewById(R.id.toolbar)) supportActionBar!!.setDisplayHomeAsUpEnabled(true) - swipeRefresh = findViewById(R.id.swipe_refresh) - scrollView = findViewById(R.id.scroll_view) - logText = findViewById(R.id.log_text) + swipeRefresh = requireViewById(R.id.swipe_refresh) + scrollView = requireViewById(R.id.scroll_view) + logText = requireViewById(R.id.log_text) swipeRefresh.setOnRefreshListener { lifecycleScope.launch { diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/MainActivity.kt b/app-common/src/main/java/im/angry/openeuicc/ui/MainActivity.kt index ca6715d9..2d80e331 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/MainActivity.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/MainActivity.kt @@ -25,20 +25,22 @@ open class MainActivity : AppCompatActivity(), OpenEuiccContextMarker { } private lateinit var spinnerAdapter: ArrayAdapter + private lateinit var spinnerItem: MenuItem private lateinit var spinner: Spinner private val fragments = arrayListOf() - private lateinit var noEuiccPlaceholder: View - protected lateinit var tm: TelephonyManager override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) - setSupportActionBar(findViewById(R.id.toolbar)) + setSupportActionBar(requireViewById(R.id.toolbar)) - noEuiccPlaceholder = findViewById(R.id.no_euicc_placeholder) + supportFragmentManager.beginTransaction().replace( + R.id.fragment_root, + appContainer.uiComponentFactory.createNoEuiccPlaceholderFragment() + ).commit() tm = telephonyManager @@ -53,7 +55,11 @@ open class MainActivity : AppCompatActivity(), OpenEuiccContextMarker { menuInflater.inflate(R.menu.activity_main, menu) if (!this::spinner.isInitialized) { - spinner = menu.findItem(R.id.spinner).actionView as Spinner + spinnerItem = menu.findItem(R.id.spinner) + spinner = spinnerItem.actionView as Spinner + if (spinnerAdapter.isEmpty) { + spinnerItem.isVisible = false + } spinner.adapter = spinnerAdapter spinner.onItemSelectedListener = object : AdapterView.OnItemSelectedListener { override fun onItemSelected( @@ -108,7 +114,9 @@ open class MainActivity : AppCompatActivity(), OpenEuiccContextMarker { } if (fragments.isNotEmpty()) { - noEuiccPlaceholder.visibility = View.GONE + if (this@MainActivity::spinner.isInitialized) { + spinnerItem.isVisible = true + } supportFragmentManager.beginTransaction().replace(R.id.fragment_root, fragments.first()).commit() } } diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/NoEuiccPlaceholderFragment.kt b/app-common/src/main/java/im/angry/openeuicc/ui/NoEuiccPlaceholderFragment.kt new file mode 100644 index 00000000..e9e44b11 --- /dev/null +++ b/app-common/src/main/java/im/angry/openeuicc/ui/NoEuiccPlaceholderFragment.kt @@ -0,0 +1,18 @@ +package im.angry.openeuicc.ui + +import android.os.Bundle +import android.view.LayoutInflater +import android.view.View +import android.view.ViewGroup +import androidx.fragment.app.Fragment +import im.angry.openeuicc.common.R + +class NoEuiccPlaceholderFragment : Fragment() { + override fun onCreateView( + inflater: LayoutInflater, + container: ViewGroup?, + savedInstanceState: Bundle? + ): View? { + return inflater.inflate(R.layout.fragment_no_euicc_placeholder, container, false) + } +} \ No newline at end of file diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/NotificationsActivity.kt b/app-common/src/main/java/im/angry/openeuicc/ui/NotificationsActivity.kt index 87c5ba34..925ed84b 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/NotificationsActivity.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/NotificationsActivity.kt @@ -37,14 +37,14 @@ class NotificationsActivity: AppCompatActivity(), OpenEuiccContextMarker { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_notifications) - setSupportActionBar(findViewById(R.id.toolbar)) + setSupportActionBar(requireViewById(R.id.toolbar)) supportActionBar!!.setDisplayHomeAsUpEnabled(true) euiccChannel = euiccChannelManager .findEuiccChannelBySlotBlocking(intent.getIntExtra("logicalSlotId", 0))!! - swipeRefresh = findViewById(R.id.swipe_refresh) - notificationList = findViewById(R.id.recycler_view) + swipeRefresh = requireViewById(R.id.swipe_refresh) + notificationList = requireViewById(R.id.recycler_view) notificationList.layoutManager = LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false) @@ -118,8 +118,8 @@ class NotificationsActivity: AppCompatActivity(), OpenEuiccContextMarker { @SuppressLint("ClickableViewAccessibility") inner class NotificationViewHolder(private val root: View): RecyclerView.ViewHolder(root), View.OnCreateContextMenuListener, OnMenuItemClickListener { - private val address: TextView = root.findViewById(R.id.notification_address) - private val profileName: TextView = root.findViewById(R.id.notification_profile_name) + private val address: TextView = root.requireViewById(R.id.notification_address) + private val profileName: TextView = root.requireViewById(R.id.notification_profile_name) private lateinit var notification: LocalProfileNotificationWrapper diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/ProfileDownloadFragment.kt b/app-common/src/main/java/im/angry/openeuicc/ui/ProfileDownloadFragment.kt index 43fc1ee9..8ab09d91 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/ProfileDownloadFragment.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/ProfileDownloadFragment.kt @@ -69,13 +69,13 @@ class ProfileDownloadFragment : BaseMaterialDialogFragment(), ): View { val view = inflater.inflate(R.layout.fragment_profile_download, container, false) - toolbar = view.findViewById(R.id.toolbar) - profileDownloadServer = view.findViewById(R.id.profile_download_server) - profileDownloadCode = view.findViewById(R.id.profile_download_code) - profileDownloadConfirmationCode = view.findViewById(R.id.profile_download_confirmation_code) - profileDownloadIMEI = view.findViewById(R.id.profile_download_imei) - profileDownloadFreeSpace = view.findViewById(R.id.profile_download_free_space) - progress = view.findViewById(R.id.progress) + toolbar = view.requireViewById(R.id.toolbar) + profileDownloadServer = view.requireViewById(R.id.profile_download_server) + profileDownloadCode = view.requireViewById(R.id.profile_download_code) + profileDownloadConfirmationCode = view.requireViewById(R.id.profile_download_confirmation_code) + profileDownloadIMEI = view.requireViewById(R.id.profile_download_imei) + profileDownloadFreeSpace = view.requireViewById(R.id.profile_download_free_space) + progress = view.requireViewById(R.id.progress) toolbar.inflateMenu(R.menu.fragment_profile_download) diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/ProfileRenameFragment.kt b/app-common/src/main/java/im/angry/openeuicc/ui/ProfileRenameFragment.kt index 7ebac399..79871173 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/ProfileRenameFragment.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/ProfileRenameFragment.kt @@ -46,9 +46,9 @@ class ProfileRenameFragment : BaseMaterialDialogFragment(), EuiccChannelFragment ): View { val view = inflater.inflate(R.layout.fragment_profile_rename, container, false) - toolbar = view.findViewById(R.id.toolbar) - profileRenameNewName = view.findViewById(R.id.profile_rename_new_name) - progress = view.findViewById(R.id.progress) + toolbar = view.requireViewById(R.id.toolbar) + profileRenameNewName = view.requireViewById(R.id.profile_rename_new_name) + progress = view.requireViewById(R.id.progress) toolbar.inflateMenu(R.menu.fragment_profile_rename) diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/SettingsActivity.kt b/app-common/src/main/java/im/angry/openeuicc/ui/SettingsActivity.kt index f5bb4d48..426c5467 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/SettingsActivity.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/SettingsActivity.kt @@ -9,7 +9,7 @@ class SettingsActivity: AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_settings) - setSupportActionBar(findViewById(R.id.toolbar)) + setSupportActionBar(requireViewById(R.id.toolbar)) supportActionBar!!.setDisplayHomeAsUpEnabled(true) supportFragmentManager.beginTransaction() .replace(R.id.settings_container, SettingsFragment()) diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/SlotSelectFragment.kt b/app-common/src/main/java/im/angry/openeuicc/ui/SlotSelectFragment.kt index 9bdcbc10..6288b0df 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/SlotSelectFragment.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/SlotSelectFragment.kt @@ -39,13 +39,13 @@ class SlotSelectFragment : BaseMaterialDialogFragment(), OpenEuiccContextMarker ): View? { val view = inflater.inflate(R.layout.fragment_slot_select, container, false) - toolbar = view.findViewById(R.id.toolbar) + toolbar = view.requireViewById(R.id.toolbar) toolbar.setTitle(R.string.slot_select) toolbar.inflateMenu(R.menu.fragment_slot_select) val adapter = ArrayAdapter(inflater.context, R.layout.spinner_item) - spinner = view.findViewById(R.id.spinner) + spinner = view.requireViewById(R.id.spinner) spinner.adapter = adapter channels.forEach { channel -> diff --git a/app-common/src/main/java/im/angry/openeuicc/ui/preference/LongSummaryPreferenceCategory.kt b/app-common/src/main/java/im/angry/openeuicc/ui/preference/LongSummaryPreferenceCategory.kt index a35e897b..dc16e15f 100644 --- a/app-common/src/main/java/im/angry/openeuicc/ui/preference/LongSummaryPreferenceCategory.kt +++ b/app-common/src/main/java/im/angry/openeuicc/ui/preference/LongSummaryPreferenceCategory.kt @@ -18,4 +18,4 @@ class LongSummaryPreferenceCategory: PreferenceCategory { summaryText.isSingleLine = false summaryText.maxLines = 10 } -} \ No newline at end of file +} diff --git a/app-common/src/main/java/im/angry/openeuicc/util/Utils.kt b/app-common/src/main/java/im/angry/openeuicc/util/Utils.kt index 33699d7e..175e85fa 100644 --- a/app-common/src/main/java/im/angry/openeuicc/util/Utils.kt +++ b/app-common/src/main/java/im/angry/openeuicc/util/Utils.kt @@ -24,7 +24,7 @@ val Context.selfAppVersion: String get() = try { val pInfo = packageManager.getPackageInfo(packageName, 0) - pInfo.versionName + pInfo.versionName!! } catch (e: PackageManager.NameNotFoundException) { throw RuntimeException(e) } @@ -91,4 +91,4 @@ suspend fun connectSEService(context: Context): SEService = suspendCoroutine { c } } } -} \ No newline at end of file +} diff --git a/app-common/src/main/res/layout/activity_main.xml b/app-common/src/main/res/layout/activity_main.xml index 74b77993..4f1020d7 100644 --- a/app-common/src/main/res/layout/activity_main.xml +++ b/app-common/src/main/res/layout/activity_main.xml @@ -21,15 +21,6 @@ app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintLeft_toLeftOf="parent" app:layout_constraintRight_toRightOf="parent" - app:layout_constraintTop_toBottomOf="@id/toolbar"> - - + app:layout_constraintTop_toBottomOf="@id/toolbar"/> \ No newline at end of file diff --git a/app-common/src/main/res/layout/fragment_no_euicc_placeholder.xml b/app-common/src/main/res/layout/fragment_no_euicc_placeholder.xml new file mode 100644 index 00000000..b040fda6 --- /dev/null +++ b/app-common/src/main/res/layout/fragment_no_euicc_placeholder.xml @@ -0,0 +1,13 @@ + + + + \ No newline at end of file diff --git a/app-common/src/main/res/values/strings.xml b/app-common/src/main/res/values/strings.xml index 040c910f..52187850 100644 --- a/app-common/src/main/res/values/strings.xml +++ b/app-common/src/main/res/values/strings.xml @@ -1,6 +1,6 @@ - No eUICC card on this device is accessible by this app.\nInsert a supported eUICC card, or try out the privileged OpenEUICC app instead. + No removable eUICC card accessible by this app is detected on this device. Unknown Help diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/UnprivilegedOpenEuiccApplication.kt b/app-unpriv/src/main/java/im/angry/openeuicc/UnprivilegedOpenEuiccApplication.kt index 23e7be9d..55415012 100644 --- a/app-unpriv/src/main/java/im/angry/openeuicc/UnprivilegedOpenEuiccApplication.kt +++ b/app-unpriv/src/main/java/im/angry/openeuicc/UnprivilegedOpenEuiccApplication.kt @@ -1,12 +1,17 @@ package im.angry.openeuicc import android.content.Intent +import im.angry.openeuicc.di.UnprivilegedAppContainer import im.angry.openeuicc.ui.LogsActivity import im.angry.openeuicc.util.* import kotlinx.coroutines.runBlocking import kotlin.system.exitProcess class UnprivilegedOpenEuiccApplication : OpenEuiccApplication() { + override val appContainer by lazy { + UnprivilegedAppContainer(this) + } + override fun onCreate() { super.onCreate() diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/di/UnprivilegedAppContainer.kt b/app-unpriv/src/main/java/im/angry/openeuicc/di/UnprivilegedAppContainer.kt new file mode 100644 index 00000000..22d5a62d --- /dev/null +++ b/app-unpriv/src/main/java/im/angry/openeuicc/di/UnprivilegedAppContainer.kt @@ -0,0 +1,9 @@ +package im.angry.openeuicc.di + +import android.content.Context + +class UnprivilegedAppContainer(context: Context) : DefaultAppContainer(context) { + override val uiComponentFactory by lazy { + UnprivilegedUiComponentFactory() + } +} \ No newline at end of file diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/di/UnprivilegedUiComponentFactory.kt b/app-unpriv/src/main/java/im/angry/openeuicc/di/UnprivilegedUiComponentFactory.kt new file mode 100644 index 00000000..f1170382 --- /dev/null +++ b/app-unpriv/src/main/java/im/angry/openeuicc/di/UnprivilegedUiComponentFactory.kt @@ -0,0 +1,9 @@ +package im.angry.openeuicc.di + +import androidx.fragment.app.Fragment +import im.angry.openeuicc.ui.UnprivilegedNoEuiccPlaceholderFragment + +class UnprivilegedUiComponentFactory : DefaultUiComponentFactory() { + override fun createNoEuiccPlaceholderFragment(): Fragment = + UnprivilegedNoEuiccPlaceholderFragment() +} \ No newline at end of file diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/ui/CompatibilityCheckActivity.kt b/app-unpriv/src/main/java/im/angry/openeuicc/ui/CompatibilityCheckActivity.kt index b7c8cf80..b747befe 100644 --- a/app-unpriv/src/main/java/im/angry/openeuicc/ui/CompatibilityCheckActivity.kt +++ b/app-unpriv/src/main/java/im/angry/openeuicc/ui/CompatibilityCheckActivity.kt @@ -24,10 +24,10 @@ class CompatibilityCheckActivity: AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_compatibility_check) - setSupportActionBar(findViewById(R.id.toolbar)) + setSupportActionBar(requireViewById(R.id.toolbar)) supportActionBar!!.setDisplayHomeAsUpEnabled(true) - compatibilityCheckList = findViewById(R.id.recycler_view) + compatibilityCheckList = requireViewById(R.id.recycler_view) compatibilityCheckList.layoutManager = LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false) compatibilityCheckList.addItemDecoration(DividerItemDecoration(this, LinearLayoutManager.VERTICAL)) @@ -51,9 +51,9 @@ class CompatibilityCheckActivity: AppCompatActivity() { } inner class ViewHolder(private val root: View): RecyclerView.ViewHolder(root) { - private val titleView: TextView = root.findViewById(R.id.compatibility_check_title) - private val descView: TextView = root.findViewById(R.id.compatibility_check_desc) - private val statusContainer: ViewGroup = root.findViewById(R.id.compatibility_check_status_container) + private val titleView: TextView = root.requireViewById(R.id.compatibility_check_title) + private val descView: TextView = root.requireViewById(R.id.compatibility_check_desc) + private val statusContainer: ViewGroup = root.requireViewById(R.id.compatibility_check_status_container) fun bindItem(item: CompatibilityCheck) { titleView.text = item.title @@ -65,16 +65,16 @@ class CompatibilityCheckActivity: AppCompatActivity() { when (item.state) { CompatibilityCheck.State.SUCCESS -> { - root.findViewById(R.id.compatibility_check_checkmark).visibility = View.VISIBLE + root.requireViewById(R.id.compatibility_check_checkmark).visibility = View.VISIBLE } CompatibilityCheck.State.FAILURE -> { - root.findViewById(R.id.compatibility_check_error).visibility = View.VISIBLE + root.requireViewById(R.id.compatibility_check_error).visibility = View.VISIBLE } CompatibilityCheck.State.FAILURE_UNKNOWN -> { - root.findViewById(R.id.compatibility_check_unknown).visibility = View.VISIBLE + root.requireViewById(R.id.compatibility_check_unknown).visibility = View.VISIBLE } else -> { - root.findViewById(R.id.compatibility_check_progress_bar).visibility = View.VISIBLE + root.requireViewById(R.id.compatibility_check_progress_bar).visibility = View.VISIBLE } } } diff --git a/app-unpriv/src/main/java/im/angry/openeuicc/ui/UnprivilegedNoEuiccPlaceholderFragment.kt b/app-unpriv/src/main/java/im/angry/openeuicc/ui/UnprivilegedNoEuiccPlaceholderFragment.kt new file mode 100644 index 00000000..92cda23b --- /dev/null +++ b/app-unpriv/src/main/java/im/angry/openeuicc/ui/UnprivilegedNoEuiccPlaceholderFragment.kt @@ -0,0 +1,29 @@ +package im.angry.openeuicc.ui + +import android.content.Intent +import android.os.Bundle +import android.view.LayoutInflater +import android.view.View +import android.view.ViewGroup +import androidx.fragment.app.Fragment +import im.angry.easyeuicc.R + +class UnprivilegedNoEuiccPlaceholderFragment : Fragment() { + override fun onCreateView( + inflater: LayoutInflater, + container: ViewGroup?, + savedInstanceState: Bundle? + ): View? { + val view = inflater.inflate( + R.layout.fragment_no_euicc_placeholder_unprivileged, + container, + false + ) + + view.findViewById(R.id.compatibility_check).setOnClickListener { + startActivity(Intent(requireContext(), CompatibilityCheckActivity::class.java)) + } + + return view + } +} \ No newline at end of file diff --git a/app-unpriv/src/main/res/layout/fragment_no_euicc_placeholder_unprivileged.xml b/app-unpriv/src/main/res/layout/fragment_no_euicc_placeholder_unprivileged.xml new file mode 100644 index 00000000..7f9e65c0 --- /dev/null +++ b/app-unpriv/src/main/res/layout/fragment_no_euicc_placeholder_unprivileged.xml @@ -0,0 +1,28 @@ + + + + + + + + \ No newline at end of file diff --git a/app/src/main/java/im/angry/openeuicc/core/PrivilegedEuiccChannelFactory.kt b/app/src/main/java/im/angry/openeuicc/core/PrivilegedEuiccChannelFactory.kt index 78acefe1..317248b8 100644 --- a/app/src/main/java/im/angry/openeuicc/core/PrivilegedEuiccChannelFactory.kt +++ b/app/src/main/java/im/angry/openeuicc/core/PrivilegedEuiccChannelFactory.kt @@ -26,9 +26,7 @@ class PrivilegedEuiccChannelFactory(context: Context) : DefaultEuiccChannelFacto "Trying TelephonyManager for slot ${port.card.physicalSlotIndex} port ${port.portIndex}" ) try { - return TelephonyManagerChannel( - port, tm - ) + return EuiccChannel(port, TelephonyManagerApduInterface(port, tm)) } catch (e: IllegalArgumentException) { // Failed Log.w( diff --git a/app/src/main/java/im/angry/openeuicc/core/TelephonyManagerApduInterface.kt b/app/src/main/java/im/angry/openeuicc/core/TelephonyManagerApduInterface.kt index c0936a46..d6770c3c 100644 --- a/app/src/main/java/im/angry/openeuicc/core/TelephonyManagerApduInterface.kt +++ b/app/src/main/java/im/angry/openeuicc/core/TelephonyManagerApduInterface.kt @@ -3,10 +3,7 @@ package im.angry.openeuicc.core import android.telephony.IccOpenLogicalChannelResponse import android.telephony.TelephonyManager import im.angry.openeuicc.util.* -import net.typeblog.lpac_jni.LocalProfileAssistant import net.typeblog.lpac_jni.ApduInterface -import net.typeblog.lpac_jni.impl.HttpInterfaceImpl -import net.typeblog.lpac_jni.impl.LocalProfileAssistantImpl class TelephonyManagerApduInterface( private val port: UiccPortInfoCompat, @@ -54,14 +51,4 @@ class TelephonyManagerApduInterface( cla, instruction, p1, p2, p3, p4)?.decodeHex() ?: byteArrayOf() } -} - -class TelephonyManagerChannel( - port: UiccPortInfoCompat, - private val tm: TelephonyManager -) : EuiccChannel(port) { - override val lpa: LocalProfileAssistant = LocalProfileAssistantImpl( - TelephonyManagerApduInterface(port, tm), - HttpInterfaceImpl() - ) } \ No newline at end of file diff --git a/app/src/main/java/im/angry/openeuicc/service/OpenEuiccService.kt b/app/src/main/java/im/angry/openeuicc/service/OpenEuiccService.kt index 23f14442..3c9eaf26 100644 --- a/app/src/main/java/im/angry/openeuicc/service/OpenEuiccService.kt +++ b/app/src/main/java/im/angry/openeuicc/service/OpenEuiccService.kt @@ -104,9 +104,9 @@ class OpenEuiccService : EuiccService(), OpenEuiccContextMarker { return GetDefaultDownloadableSubscriptionListResult(RESULT_OK, arrayOf()) } - override fun onGetEuiccProfileInfoList(slotId: Int): GetEuiccProfileInfoListResult? { + override fun onGetEuiccProfileInfoList(slotId: Int): GetEuiccProfileInfoListResult { Log.i(TAG, "onGetEuiccProfileInfoList slotId=$slotId") - val channel = findChannel(slotId) ?: return null + val channel = findChannel(slotId)!! val profiles = channel.lpa.profiles.operational.map { EuiccProfileInfo.Builder(it.iccid).apply { setProfileName(it.name) @@ -256,4 +256,4 @@ class OpenEuiccService : EuiccService(), OpenEuiccContextMarker { // No-op -- we do not care return RESULT_FIRST_USER } -} \ No newline at end of file +} diff --git a/app/src/main/java/im/angry/openeuicc/ui/LuiActivity.kt b/app/src/main/java/im/angry/openeuicc/ui/LuiActivity.kt index e60dfa72..f12c9b4e 100644 --- a/app/src/main/java/im/angry/openeuicc/ui/LuiActivity.kt +++ b/app/src/main/java/im/angry/openeuicc/ui/LuiActivity.kt @@ -10,10 +10,10 @@ class LuiActivity : AppCompatActivity() { super.onStart() setContentView(R.layout.activity_lui) - findViewById(R.id.lui_skip).setOnClickListener { finish() } + requireViewById(R.id.lui_skip).setOnClickListener { finish() } // TODO: Deactivate LuiActivity if there is no eSIM found. // TODO: Support pre-filled download info (from carrier apps); UX - findViewById(R.id.lui_download).setOnClickListener { + requireViewById(R.id.lui_download).setOnClickListener { startActivity(Intent(this, DirectProfileDownloadActivity::class.java)) } } diff --git a/app/src/main/java/im/angry/openeuicc/ui/PrivilegedEuiccManagementFragment.kt b/app/src/main/java/im/angry/openeuicc/ui/PrivilegedEuiccManagementFragment.kt index 78fcd4f5..744acb8b 100644 --- a/app/src/main/java/im/angry/openeuicc/ui/PrivilegedEuiccManagementFragment.kt +++ b/app/src/main/java/im/angry/openeuicc/ui/PrivilegedEuiccManagementFragment.kt @@ -17,7 +17,7 @@ class PrivilegedEuiccManagementFragment: EuiccManagementFragment() { override suspend fun onCreateFooterViews(parent: ViewGroup): List = if (channel.isMEP) { val view = layoutInflater.inflate(R.layout.footer_mep, parent, false) - view.findViewById