Compare commits
5 commits
c44ec22a63
...
ca637da5ee
Author | SHA1 | Date | |
---|---|---|---|
ca637da5ee | |||
e407ab0e79 | |||
27ca07cde0 | |||
3219497cb0 | |||
9c376d0a3c |
14 changed files with 261 additions and 7 deletions
3
.idea/misc.xml
generated
3
.idea/misc.xml
generated
|
@ -3,10 +3,13 @@
|
||||||
<component name="DesignSurface">
|
<component name="DesignSurface">
|
||||||
<option name="filePathToZoomLevelMap">
|
<option name="filePathToZoomLevelMap">
|
||||||
<map>
|
<map>
|
||||||
|
<entry key="app/src/main/res/drawable/ic_add.xml" value="0.2015" />
|
||||||
<entry key="app/src/main/res/layout/activity_main.xml" value="0.19375" />
|
<entry key="app/src/main/res/layout/activity_main.xml" value="0.19375" />
|
||||||
<entry key="app/src/main/res/layout/euicc_profile.xml" value="0.19375" />
|
<entry key="app/src/main/res/layout/euicc_profile.xml" value="0.19375" />
|
||||||
<entry key="app/src/main/res/layout/fragment_euicc.xml" value="0.19375" />
|
<entry key="app/src/main/res/layout/fragment_euicc.xml" value="0.19375" />
|
||||||
|
<entry key="app/src/main/res/layout/fragment_profile_download.xml" value="0.19375" />
|
||||||
<entry key="app/src/main/res/menu/activity_main_slot_spinner.xml" value="0.19375" />
|
<entry key="app/src/main/res/menu/activity_main_slot_spinner.xml" value="0.19375" />
|
||||||
|
<entry key="app/src/main/res/menu/fragment_profile_download.xml" value="0.19375" />
|
||||||
</map>
|
</map>
|
||||||
</option>
|
</option>
|
||||||
</component>
|
</component>
|
||||||
|
|
|
@ -44,6 +44,7 @@ dependencies {
|
||||||
implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.4.1'
|
implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.4.1'
|
||||||
implementation "androidx.swiperefreshlayout:swiperefreshlayout:1.1.0"
|
implementation "androidx.swiperefreshlayout:swiperefreshlayout:1.1.0"
|
||||||
implementation "androidx.cardview:cardview:1.0.0"
|
implementation "androidx.cardview:cardview:1.0.0"
|
||||||
|
implementation 'com.journeyapps:zxing-android-embedded:4.3.0'
|
||||||
testImplementation 'junit:junit:4.13.2'
|
testImplementation 'junit:junit:4.13.2'
|
||||||
androidTestImplementation 'androidx.test.ext:junit:1.1.3'
|
androidTestImplementation 'androidx.test.ext:junit:1.1.3'
|
||||||
androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0'
|
androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0'
|
||||||
|
|
|
@ -11,6 +11,7 @@
|
||||||
<uses-permission android:name="android.permission.SECURE_ELEMENT_PRIVILEGED_OPERATION" />
|
<uses-permission android:name="android.permission.SECURE_ELEMENT_PRIVILEGED_OPERATION" />
|
||||||
|
|
||||||
<application
|
<application
|
||||||
|
android:name=".OpenEUICCApplication"
|
||||||
android:allowBackup="true"
|
android:allowBackup="true"
|
||||||
android:icon="@mipmap/ic_launcher"
|
android:icon="@mipmap/ic_launcher"
|
||||||
android:label="@string/app_name"
|
android:label="@string/app_name"
|
||||||
|
@ -26,6 +27,11 @@
|
||||||
<category android:name="android.intent.category.LAUNCHER" />
|
<category android:name="android.intent.category.LAUNCHER" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</activity>
|
</activity>
|
||||||
|
|
||||||
|
<activity
|
||||||
|
android:name="com.journeyapps.barcodescanner.CaptureActivity"
|
||||||
|
android:screenOrientation="fullSensor"
|
||||||
|
tools:replace="screenOrientation" />
|
||||||
</application>
|
</application>
|
||||||
|
|
||||||
</manifest>
|
</manifest>
|
|
@ -0,0 +1,8 @@
|
||||||
|
package im.angry.openeuicc
|
||||||
|
|
||||||
|
import android.app.Application
|
||||||
|
import im.angry.openeuicc.core.EuiccChannelRepositoryProxy
|
||||||
|
|
||||||
|
class OpenEUICCApplication : Application() {
|
||||||
|
val euiccChannelRepo = EuiccChannelRepositoryProxy(this)
|
||||||
|
}
|
|
@ -0,0 +1,23 @@
|
||||||
|
package im.angry.openeuicc.ui
|
||||||
|
|
||||||
|
import android.os.Bundle
|
||||||
|
import androidx.fragment.app.Fragment
|
||||||
|
import im.angry.openeuicc.OpenEUICCApplication
|
||||||
|
import im.angry.openeuicc.core.EuiccChannel
|
||||||
|
|
||||||
|
interface EuiccFragmentMarker
|
||||||
|
|
||||||
|
fun <T> newInstanceEuicc(clazz: Class<T>, slotId: Int): T where T: Fragment, T: EuiccFragmentMarker {
|
||||||
|
val instance = clazz.newInstance()
|
||||||
|
instance.arguments = Bundle().apply {
|
||||||
|
putInt("slotId", slotId)
|
||||||
|
}
|
||||||
|
return instance
|
||||||
|
}
|
||||||
|
|
||||||
|
val <T> T.slotId: Int where T: Fragment, T: EuiccFragmentMarker
|
||||||
|
get() = requireArguments().getInt("slotId")
|
||||||
|
|
||||||
|
val <T> T.channel: EuiccChannel where T: Fragment, T: EuiccFragmentMarker
|
||||||
|
get() =
|
||||||
|
(requireActivity().application as OpenEUICCApplication).euiccChannelRepo.availableChannels[slotId]
|
|
@ -11,14 +11,18 @@ import androidx.lifecycle.lifecycleScope
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
import androidx.recyclerview.widget.LinearLayoutManager
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
import im.angry.openeuicc.R
|
import im.angry.openeuicc.R
|
||||||
import im.angry.openeuicc.core.EuiccChannel
|
|
||||||
import im.angry.openeuicc.databinding.EuiccProfileBinding
|
import im.angry.openeuicc.databinding.EuiccProfileBinding
|
||||||
import im.angry.openeuicc.databinding.FragmentEuiccBinding
|
import im.angry.openeuicc.databinding.FragmentEuiccBinding
|
||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
import kotlinx.coroutines.withContext
|
import kotlinx.coroutines.withContext
|
||||||
|
|
||||||
class EuiccManagementFragment(private val channel: EuiccChannel) : Fragment() {
|
class EuiccManagementFragment : Fragment(), EuiccFragmentMarker {
|
||||||
|
companion object {
|
||||||
|
fun newInstance(slotId: Int): EuiccManagementFragment =
|
||||||
|
newInstanceEuicc(EuiccManagementFragment::class.java, slotId)
|
||||||
|
}
|
||||||
|
|
||||||
private var _binding: FragmentEuiccBinding? = null
|
private var _binding: FragmentEuiccBinding? = null
|
||||||
private val binding get() = _binding!!
|
private val binding get() = _binding!!
|
||||||
|
|
||||||
|
@ -39,6 +43,11 @@ class EuiccManagementFragment(private val channel: EuiccChannel) : Fragment() {
|
||||||
binding.profileList.adapter = adapter
|
binding.profileList.adapter = adapter
|
||||||
binding.profileList.layoutManager =
|
binding.profileList.layoutManager =
|
||||||
LinearLayoutManager(view.context, LinearLayoutManager.VERTICAL, false)
|
LinearLayoutManager(view.context, LinearLayoutManager.VERTICAL, false)
|
||||||
|
|
||||||
|
binding.fab.setOnClickListener {
|
||||||
|
ProfileDownloadFragment.newInstance(slotId)
|
||||||
|
.show(childFragmentManager, ProfileDownloadFragment.TAG)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onStart() {
|
override fun onStart() {
|
||||||
|
|
|
@ -9,8 +9,9 @@ import android.widget.ArrayAdapter
|
||||||
import android.widget.Spinner
|
import android.widget.Spinner
|
||||||
import androidx.appcompat.app.AppCompatActivity
|
import androidx.appcompat.app.AppCompatActivity
|
||||||
import androidx.lifecycle.lifecycleScope
|
import androidx.lifecycle.lifecycleScope
|
||||||
|
import im.angry.openeuicc.OpenEUICCApplication
|
||||||
import im.angry.openeuicc.R
|
import im.angry.openeuicc.R
|
||||||
import im.angry.openeuicc.core.EuiccChannelRepositoryProxy
|
import im.angry.openeuicc.core.EuiccChannelRepository
|
||||||
import im.angry.openeuicc.databinding.ActivityMainBinding
|
import im.angry.openeuicc.databinding.ActivityMainBinding
|
||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
|
@ -21,7 +22,7 @@ class MainActivity : AppCompatActivity() {
|
||||||
const val TAG = "MainActivity"
|
const val TAG = "MainActivity"
|
||||||
}
|
}
|
||||||
|
|
||||||
private val repo = EuiccChannelRepositoryProxy(this)
|
private lateinit var repo: EuiccChannelRepository
|
||||||
|
|
||||||
private lateinit var spinnerAdapter: ArrayAdapter<String>
|
private lateinit var spinnerAdapter: ArrayAdapter<String>
|
||||||
private lateinit var spinner: Spinner
|
private lateinit var spinner: Spinner
|
||||||
|
@ -35,6 +36,8 @@ class MainActivity : AppCompatActivity() {
|
||||||
binding = ActivityMainBinding.inflate(layoutInflater)
|
binding = ActivityMainBinding.inflate(layoutInflater)
|
||||||
setContentView(binding.root)
|
setContentView(binding.root)
|
||||||
|
|
||||||
|
repo = (application as OpenEUICCApplication).euiccChannelRepo
|
||||||
|
|
||||||
spinnerAdapter = ArrayAdapter<String>(this, android.R.layout.simple_spinner_item)
|
spinnerAdapter = ArrayAdapter<String>(this, android.R.layout.simple_spinner_item)
|
||||||
|
|
||||||
lifecycleScope.launch {
|
lifecycleScope.launch {
|
||||||
|
@ -75,9 +78,9 @@ class MainActivity : AppCompatActivity() {
|
||||||
}
|
}
|
||||||
|
|
||||||
withContext(Dispatchers.Main) {
|
withContext(Dispatchers.Main) {
|
||||||
repo.availableChannels.forEach {
|
repo.availableChannels.forEachIndexed { idx, channel ->
|
||||||
spinnerAdapter.add(it.name)
|
spinnerAdapter.add(channel.name)
|
||||||
fragments.add(EuiccManagementFragment(it))
|
fragments.add(EuiccManagementFragment.newInstance(idx))
|
||||||
}
|
}
|
||||||
|
|
||||||
if (fragments.isNotEmpty()) {
|
if (fragments.isNotEmpty()) {
|
||||||
|
|
|
@ -0,0 +1,78 @@
|
||||||
|
package im.angry.openeuicc.ui
|
||||||
|
|
||||||
|
import android.app.Dialog
|
||||||
|
import android.os.Bundle
|
||||||
|
import android.view.*
|
||||||
|
import androidx.appcompat.widget.Toolbar
|
||||||
|
import androidx.fragment.app.DialogFragment
|
||||||
|
import com.journeyapps.barcodescanner.ScanContract
|
||||||
|
import com.journeyapps.barcodescanner.ScanOptions
|
||||||
|
import im.angry.openeuicc.R
|
||||||
|
import im.angry.openeuicc.databinding.FragmentProfileDownloadBinding
|
||||||
|
import im.angry.openeuicc.util.setWidthPercent
|
||||||
|
|
||||||
|
class ProfileDownloadFragment : DialogFragment(), EuiccFragmentMarker, Toolbar.OnMenuItemClickListener {
|
||||||
|
companion object {
|
||||||
|
const val TAG = "ProfileDownloadFragment"
|
||||||
|
|
||||||
|
fun newInstance(slotId: Int): ProfileDownloadFragment =
|
||||||
|
newInstanceEuicc(ProfileDownloadFragment::class.java, slotId)
|
||||||
|
}
|
||||||
|
|
||||||
|
private var _binding: FragmentProfileDownloadBinding? = null
|
||||||
|
private val binding get() = _binding!!
|
||||||
|
|
||||||
|
private val barcodeScannerLauncher = registerForActivityResult(ScanContract()) { result ->
|
||||||
|
result.contents?.let { content ->
|
||||||
|
val components = content.split("$")
|
||||||
|
if (components.size != 3 || components[0] != "LPA:1") return@registerForActivityResult
|
||||||
|
binding.profileDownloadServer.editText?.setText(components[1])
|
||||||
|
binding.profileDownloadCode.editText?.setText(components[2])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onCreateView(
|
||||||
|
inflater: LayoutInflater,
|
||||||
|
container: ViewGroup?,
|
||||||
|
savedInstanceState: Bundle?
|
||||||
|
): View {
|
||||||
|
_binding = FragmentProfileDownloadBinding.inflate(inflater, container, false)
|
||||||
|
binding.toolbar.inflateMenu(R.menu.fragment_profile_download)
|
||||||
|
return binding.root
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||||
|
super.onViewCreated(view, savedInstanceState)
|
||||||
|
binding.toolbar.apply {
|
||||||
|
setTitle(R.string.profile_download)
|
||||||
|
setNavigationOnClickListener {
|
||||||
|
dismiss()
|
||||||
|
}
|
||||||
|
setOnMenuItemClickListener(this@ProfileDownloadFragment)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onMenuItemClick(item: MenuItem): Boolean =
|
||||||
|
when (item.itemId) {
|
||||||
|
R.id.scan -> {
|
||||||
|
barcodeScannerLauncher.launch(ScanOptions().apply {
|
||||||
|
setDesiredBarcodeFormats(ScanOptions.QR_CODE)
|
||||||
|
setOrientationLocked(false)
|
||||||
|
})
|
||||||
|
true
|
||||||
|
}
|
||||||
|
else -> false
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onResume() {
|
||||||
|
super.onResume()
|
||||||
|
setWidthPercent(95)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
|
||||||
|
return super.onCreateDialog(savedInstanceState).also {
|
||||||
|
it.window?.requestFeature(Window.FEATURE_NO_TITLE)
|
||||||
|
it.setCanceledOnTouchOutside(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
28
app/src/main/java/im/angry/openeuicc/util/UiUtils.kt
Normal file
28
app/src/main/java/im/angry/openeuicc/util/UiUtils.kt
Normal file
|
@ -0,0 +1,28 @@
|
||||||
|
package im.angry.openeuicc.util
|
||||||
|
|
||||||
|
import android.content.res.Resources
|
||||||
|
import android.graphics.Rect
|
||||||
|
import android.view.ViewGroup
|
||||||
|
import androidx.fragment.app.DialogFragment
|
||||||
|
|
||||||
|
// Source: <https://stackoverflow.com/questions/12478520/how-to-set-dialogfragments-width-and-height>
|
||||||
|
/**
|
||||||
|
* Call this method (in onActivityCreated or later) to set
|
||||||
|
* the width of the dialog to a percentage of the current
|
||||||
|
* screen width.
|
||||||
|
*/
|
||||||
|
fun DialogFragment.setWidthPercent(percentage: Int) {
|
||||||
|
val percent = percentage.toFloat() / 100
|
||||||
|
val dm = Resources.getSystem().displayMetrics
|
||||||
|
val rect = dm.run { Rect(0, 0, widthPixels, heightPixels) }
|
||||||
|
val percentWidth = rect.width() * percent
|
||||||
|
dialog?.window?.setLayout(percentWidth.toInt(), ViewGroup.LayoutParams.WRAP_CONTENT)
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Call this method (in onActivityCreated or later)
|
||||||
|
* to make the dialog near-full screen.
|
||||||
|
*/
|
||||||
|
fun DialogFragment.setFullScreen() {
|
||||||
|
dialog?.window?.setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT)
|
||||||
|
}
|
10
app/src/main/res/drawable/ic_scan_black.xml
Normal file
10
app/src/main/res/drawable/ic_scan_black.xml
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
android:width="24dp"
|
||||||
|
android:height="24dp"
|
||||||
|
android:viewportWidth="24"
|
||||||
|
android:viewportHeight="24"
|
||||||
|
android:tint="?attr/colorControlNormal">
|
||||||
|
<path
|
||||||
|
android:fillColor="@android:color/white"
|
||||||
|
android:pathData="M9.5,6.5v3h-3v-3H9.5M11,5H5v6h6V5L11,5zM9.5,14.5v3h-3v-3H9.5M11,13H5v6h6V13L11,13zM17.5,6.5v3h-3v-3H17.5M19,5h-6v6h6V5L19,5zM13,13h1.5v1.5H13V13zM14.5,14.5H16V16h-1.5V14.5zM16,13h1.5v1.5H16V13zM13,16h1.5v1.5H13V16zM14.5,17.5H16V19h-1.5V17.5zM16,16h1.5v1.5H16V16zM17.5,14.5H19V16h-1.5V14.5zM17.5,17.5H19V19h-1.5V17.5zM22,7h-2V4h-3V2h5V7zM22,22v-5h-2v3h-3v2H22zM2,22h5v-2H4v-3H2V22zM2,2v5h2V4h3V2H2z"/>
|
||||||
|
</vector>
|
58
app/src/main/res/layout/fragment_profile_download.xml
Normal file
58
app/src/main/res/layout/fragment_profile_download.xml
Normal file
|
@ -0,0 +1,58 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent">
|
||||||
|
|
||||||
|
<androidx.appcompat.widget.Toolbar
|
||||||
|
android:id="@+id/toolbar"
|
||||||
|
android:layout_width="0dp"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:theme="@style/Theme.OpenEUICC"
|
||||||
|
android:background="?attr/colorPrimary"
|
||||||
|
android:elevation="4dp"
|
||||||
|
app:layout_constraintTop_toTopOf="parent"
|
||||||
|
app:layout_constraintLeft_toLeftOf="parent"
|
||||||
|
app:layout_constraintWidth_percent="1"
|
||||||
|
app:navigationIcon="?homeAsUpIndicator" />
|
||||||
|
|
||||||
|
<com.google.android.material.textfield.TextInputLayout
|
||||||
|
android:id="@+id/profile_download_server"
|
||||||
|
android:layout_width="0dp"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:layout_marginTop="15dp"
|
||||||
|
android:hint="@string/profile_download_server"
|
||||||
|
style="@style/Widget.OpenEUICC.Input"
|
||||||
|
app:layout_constraintTop_toBottomOf="@id/toolbar"
|
||||||
|
app:layout_constraintLeft_toLeftOf="parent"
|
||||||
|
app:layout_constraintRight_toRightOf="parent"
|
||||||
|
app:layout_constraintWidth_percent=".8">
|
||||||
|
|
||||||
|
<com.google.android.material.textfield.TextInputEditText
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent"
|
||||||
|
android:theme="@style/Theme.OpenEUICC.Input.Cursor"/>
|
||||||
|
|
||||||
|
</com.google.android.material.textfield.TextInputLayout>
|
||||||
|
|
||||||
|
<com.google.android.material.textfield.TextInputLayout
|
||||||
|
android:id="@+id/profile_download_code"
|
||||||
|
android:layout_width="0dp"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:layout_marginVertical="15dp"
|
||||||
|
android:hint="@string/profile_download_code"
|
||||||
|
style="@style/Widget.OpenEUICC.Input"
|
||||||
|
app:layout_constraintTop_toBottomOf="@id/profile_download_server"
|
||||||
|
app:layout_constraintLeft_toLeftOf="parent"
|
||||||
|
app:layout_constraintRight_toRightOf="parent"
|
||||||
|
app:layout_constraintBottom_toBottomOf="parent"
|
||||||
|
app:layout_constraintWidth_percent=".8">
|
||||||
|
|
||||||
|
<com.google.android.material.textfield.TextInputEditText
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent"
|
||||||
|
android:theme="@style/Theme.OpenEUICC.Input.Cursor"/>
|
||||||
|
|
||||||
|
</com.google.android.material.textfield.TextInputLayout>
|
||||||
|
|
||||||
|
</androidx.constraintlayout.widget.ConstraintLayout>
|
9
app/src/main/res/menu/fragment_profile_download.xml
Normal file
9
app/src/main/res/menu/fragment_profile_download.xml
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<menu xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
xmlns:app="http://schemas.android.com/apk/res-auto">
|
||||||
|
<item
|
||||||
|
android:id="@+id/scan"
|
||||||
|
android:icon="@drawable/ic_scan_black"
|
||||||
|
android:title="@string/profile_download_scan"
|
||||||
|
app:showAsAction="ifRoom"/>
|
||||||
|
</menu>
|
|
@ -7,4 +7,9 @@
|
||||||
<string name="disabled">Disabled</string>
|
<string name="disabled">Disabled</string>
|
||||||
<string name="provider">Provider:</string>
|
<string name="provider">Provider:</string>
|
||||||
<string name="iccid">ICCID:</string>
|
<string name="iccid">ICCID:</string>
|
||||||
|
|
||||||
|
<string name="profile_download">New eSIM</string>
|
||||||
|
<string name="profile_download_server">Server (RSP / SM-DP+)</string>
|
||||||
|
<string name="profile_download_code">Activation Code</string>
|
||||||
|
<string name="profile_download_scan">Scan QR Code</string>
|
||||||
</resources>
|
</resources>
|
|
@ -9,8 +9,21 @@
|
||||||
<item name="colorSecondary">@color/pink_600</item>
|
<item name="colorSecondary">@color/pink_600</item>
|
||||||
<item name="colorSecondaryVariant">@color/pink_800</item>
|
<item name="colorSecondaryVariant">@color/pink_800</item>
|
||||||
<item name="colorOnSecondary">@color/white</item>
|
<item name="colorOnSecondary">@color/white</item>
|
||||||
|
<item name="colorAccent">?attr/colorSecondary</item>
|
||||||
<!-- Status bar color. -->
|
<!-- Status bar color. -->
|
||||||
<item name="android:statusBarColor" tools:targetApi="l">?attr/colorPrimaryVariant</item>
|
<item name="android:statusBarColor" tools:targetApi="l">?attr/colorPrimaryVariant</item>
|
||||||
<!-- Customize your theme here. -->
|
<!-- Customize your theme here. -->
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
|
<style name="Theme.OpenEUICC.Input.Cursor" parent="ThemeOverlay.MaterialComponents.TextInputEditText.OutlinedBox">
|
||||||
|
<item name="colorControlActivated">?attr/colorSecondary</item>
|
||||||
|
</style>
|
||||||
|
|
||||||
|
<style name="Widget.OpenEUICC.Input" parent="Widget.MaterialComponents.TextInputLayout.OutlinedBox">
|
||||||
|
<item name="boxBackgroundColor">@android:color/transparent</item>
|
||||||
|
<item name="boxStrokeColor">?attr/colorSecondary</item>
|
||||||
|
<item name="hintTextColor">?attr/colorSecondary</item>
|
||||||
|
</style>
|
||||||
|
|
||||||
|
|
||||||
</resources>
|
</resources>
|
Loading…
Add table
Reference in a new issue