mirror of
https://github.com/awfixers-stuff/OwnDroid.git
synced 2026-03-23 11:05:59 +00:00
feat: change global & secure settings (#237)
This commit is contained in:
@@ -101,6 +101,8 @@ import com.bintianqi.owndroid.dpm.CrossProfileIntentFilter
|
|||||||
import com.bintianqi.owndroid.dpm.CrossProfileIntentFilterScreen
|
import com.bintianqi.owndroid.dpm.CrossProfileIntentFilterScreen
|
||||||
import com.bintianqi.owndroid.dpm.CrossProfilePackages
|
import com.bintianqi.owndroid.dpm.CrossProfilePackages
|
||||||
import com.bintianqi.owndroid.dpm.CrossProfileWidgetProviders
|
import com.bintianqi.owndroid.dpm.CrossProfileWidgetProviders
|
||||||
|
import com.bintianqi.owndroid.dpm.DefaultInputMethod
|
||||||
|
import com.bintianqi.owndroid.dpm.DefaultInputMethodScreen
|
||||||
import com.bintianqi.owndroid.dpm.DelegatedAdmins
|
import com.bintianqi.owndroid.dpm.DelegatedAdmins
|
||||||
import com.bintianqi.owndroid.dpm.DelegatedAdminsScreen
|
import com.bintianqi.owndroid.dpm.DelegatedAdminsScreen
|
||||||
import com.bintianqi.owndroid.dpm.DeleteWorkProfile
|
import com.bintianqi.owndroid.dpm.DeleteWorkProfile
|
||||||
@@ -363,6 +365,10 @@ fun Home(vm: MyViewModel, onLock: () -> Unit) {
|
|||||||
HardwareMonitorScreen(vm.hardwareProperties, vm::getHardwareProperties,
|
HardwareMonitorScreen(vm.hardwareProperties, vm::getHardwareProperties,
|
||||||
vm::setHpRefreshInterval, ::navigateUp)
|
vm::setHpRefreshInterval, ::navigateUp)
|
||||||
}
|
}
|
||||||
|
composable<DefaultInputMethod> {
|
||||||
|
DefaultInputMethodScreen(vm::getCurrentInputMethod, vm.inputMethodList,
|
||||||
|
vm::getInputMethods, vm::setDefaultInputMethod, ::navigateUp)
|
||||||
|
}
|
||||||
composable<ChangeTime> { ChangeTimeScreen(vm::setTime, ::navigateUp) }
|
composable<ChangeTime> { ChangeTimeScreen(vm::setTime, ::navigateUp) }
|
||||||
composable<ChangeTimeZone> { ChangeTimeZoneScreen(vm::setTimeZone, ::navigateUp) }
|
composable<ChangeTimeZone> { ChangeTimeZoneScreen(vm::setTimeZone, ::navigateUp) }
|
||||||
composable<AutoTimePolicy> {
|
composable<AutoTimePolicy> {
|
||||||
|
|||||||
@@ -45,7 +45,9 @@ import android.os.Bundle
|
|||||||
import android.os.HardwarePropertiesManager
|
import android.os.HardwarePropertiesManager
|
||||||
import android.os.UserHandle
|
import android.os.UserHandle
|
||||||
import android.os.UserManager
|
import android.os.UserManager
|
||||||
|
import android.provider.Settings
|
||||||
import android.telephony.data.ApnSetting
|
import android.telephony.data.ApnSetting
|
||||||
|
import android.view.inputmethod.InputMethodManager
|
||||||
import androidx.annotation.RequiresApi
|
import androidx.annotation.RequiresApi
|
||||||
import androidx.compose.ui.graphics.Color
|
import androidx.compose.ui.graphics.Color
|
||||||
import androidx.compose.ui.graphics.toArgb
|
import androidx.compose.ui.graphics.toArgb
|
||||||
@@ -103,10 +105,12 @@ import com.bintianqi.owndroid.dpm.activateOrgProfileCommand
|
|||||||
import com.bintianqi.owndroid.dpm.delegatedScopesList
|
import com.bintianqi.owndroid.dpm.delegatedScopesList
|
||||||
import com.bintianqi.owndroid.dpm.doUserOperationWithContext
|
import com.bintianqi.owndroid.dpm.doUserOperationWithContext
|
||||||
import com.bintianqi.owndroid.dpm.getPackageInstaller
|
import com.bintianqi.owndroid.dpm.getPackageInstaller
|
||||||
|
import com.bintianqi.owndroid.dpm.globalSettings
|
||||||
import com.bintianqi.owndroid.dpm.handlePrivilegeChange
|
import com.bintianqi.owndroid.dpm.handlePrivilegeChange
|
||||||
import com.bintianqi.owndroid.dpm.isValidPackageName
|
import com.bintianqi.owndroid.dpm.isValidPackageName
|
||||||
import com.bintianqi.owndroid.dpm.parsePackageInstallerMessage
|
import com.bintianqi.owndroid.dpm.parsePackageInstallerMessage
|
||||||
import com.bintianqi.owndroid.dpm.runtimePermissions
|
import com.bintianqi.owndroid.dpm.runtimePermissions
|
||||||
|
import com.bintianqi.owndroid.dpm.secureSettings
|
||||||
import com.bintianqi.owndroid.dpm.temperatureTypes
|
import com.bintianqi.owndroid.dpm.temperatureTypes
|
||||||
import com.rosan.dhizuku.api.Dhizuku
|
import com.rosan.dhizuku.api.Dhizuku
|
||||||
import com.rosan.dhizuku.api.DhizukuRequestPermissionListener
|
import com.rosan.dhizuku.api.DhizukuRequestPermissionListener
|
||||||
@@ -717,7 +721,9 @@ class MyViewModel(application: Application): AndroidViewModel(application) {
|
|||||||
commonCriteriaMode = if (VERSION.SDK_INT >= 30 && (privilege.device || privilege.org))
|
commonCriteriaMode = if (VERSION.SDK_INT >= 30 && (privilege.device || privilege.org))
|
||||||
DPM.isCommonCriteriaModeEnabled(DAR) else false,
|
DPM.isCommonCriteriaModeEnabled(DAR) else false,
|
||||||
usbSignalEnabled = if (VERSION.SDK_INT >= 31) DPM.isUsbDataSignalingEnabled else false,
|
usbSignalEnabled = if (VERSION.SDK_INT >= 31) DPM.isUsbDataSignalingEnabled else false,
|
||||||
canDisableUsbSignal = if (VERSION.SDK_INT >= 31) DPM.canUsbDataSignalingBeDisabled() else false
|
canDisableUsbSignal = if (VERSION.SDK_INT >= 31) DPM.canUsbDataSignalingBeDisabled() else false,
|
||||||
|
stayOnWhilePluggedIn = Settings.Global.getInt(
|
||||||
|
application.contentResolver, Settings.Global.STAY_ON_WHILE_PLUGGED_IN) != 0
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
fun setCameraDisabled(disabled: Boolean) {
|
fun setCameraDisabled(disabled: Boolean) {
|
||||||
@@ -782,6 +788,28 @@ class MyViewModel(application: Application): AndroidViewModel(application) {
|
|||||||
DPM.isUsbDataSignalingEnabled = enabled
|
DPM.isUsbDataSignalingEnabled = enabled
|
||||||
systemOptionsStatus.update { it.copy(usbSignalEnabled = DPM.isUsbDataSignalingEnabled) }
|
systemOptionsStatus.update { it.copy(usbSignalEnabled = DPM.isUsbDataSignalingEnabled) }
|
||||||
}
|
}
|
||||||
|
fun setStayOnWhilePluggedIn(status: Boolean) {
|
||||||
|
DPM.setGlobalSetting(
|
||||||
|
DAR, Settings.Global.STAY_ON_WHILE_PLUGGED_IN, if (status) "15" else "0"
|
||||||
|
)
|
||||||
|
systemOptionsStatus.update { it.copy(stayOnWhilePluggedIn = status) }
|
||||||
|
}
|
||||||
|
fun getGlobalSettings(): Map<String, Boolean> {
|
||||||
|
return globalSettings.associate {
|
||||||
|
it.setting to (Settings.Global.getInt(application.contentResolver, it.setting, 0) == 1)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fun setGlobalSetting(name: String, status: Boolean) {
|
||||||
|
DPM.setGlobalSetting(DAR, name, if (status) "1" else "0")
|
||||||
|
}
|
||||||
|
fun getSecureSettings(): Map<String, Boolean> {
|
||||||
|
return secureSettings.associate {
|
||||||
|
it.setting to (Settings.Secure.getInt(application.contentResolver, it.setting, 0) == 1)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fun setSecureSetting(name: String, status: Boolean) {
|
||||||
|
DPM.setSecureSetting(DAR, name, if (status) "1" else "0")
|
||||||
|
}
|
||||||
fun setKeyguardDisabled(disabled: Boolean): Boolean {
|
fun setKeyguardDisabled(disabled: Boolean): Boolean {
|
||||||
return DPM.setKeyguardDisabled(DAR, disabled)
|
return DPM.setKeyguardDisabled(DAR, disabled)
|
||||||
}
|
}
|
||||||
@@ -816,6 +844,21 @@ class MyViewModel(application: Application): AndroidViewModel(application) {
|
|||||||
delay(hpRefreshInterval)
|
delay(hpRefreshInterval)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
fun getCurrentInputMethod(): String {
|
||||||
|
return Settings.Secure.getString(
|
||||||
|
application.contentResolver, Settings.Secure.DEFAULT_INPUT_METHOD)
|
||||||
|
}
|
||||||
|
val inputMethodList = MutableStateFlow(listOf<Pair<String, AppInfo>>())
|
||||||
|
fun getInputMethods() {
|
||||||
|
val imm = application.getSystemService(InputMethodManager::class.java)
|
||||||
|
inputMethodList.value = imm.inputMethodList.map {
|
||||||
|
it.id to getAppInfo(it.packageName)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fun setDefaultInputMethod(id: String) {
|
||||||
|
DPM.setSecureSetting(DAR, Settings.Secure.DEFAULT_INPUT_METHOD, id)
|
||||||
|
getCurrentInputMethod()
|
||||||
|
}
|
||||||
@RequiresApi(28)
|
@RequiresApi(28)
|
||||||
fun setTime(time: Long, useCurrentTz: Boolean): Boolean {
|
fun setTime(time: Long, useCurrentTz: Boolean): Boolean {
|
||||||
val offset = if (useCurrentTz) {
|
val offset = if (useCurrentTz) {
|
||||||
|
|||||||
@@ -24,11 +24,13 @@ import android.net.Uri
|
|||||||
import android.os.Build.VERSION
|
import android.os.Build.VERSION
|
||||||
import android.os.HardwarePropertiesManager
|
import android.os.HardwarePropertiesManager
|
||||||
import android.os.UserManager
|
import android.os.UserManager
|
||||||
|
import android.provider.Settings
|
||||||
import androidx.activity.compose.rememberLauncherForActivityResult
|
import androidx.activity.compose.rememberLauncherForActivityResult
|
||||||
import androidx.activity.result.contract.ActivityResultContracts
|
import androidx.activity.result.contract.ActivityResultContracts
|
||||||
import androidx.annotation.RequiresApi
|
import androidx.annotation.RequiresApi
|
||||||
import androidx.compose.animation.AnimatedVisibility
|
import androidx.compose.animation.AnimatedVisibility
|
||||||
import androidx.compose.animation.animateContentSize
|
import androidx.compose.animation.animateContentSize
|
||||||
|
import androidx.compose.foundation.Image
|
||||||
import androidx.compose.foundation.background
|
import androidx.compose.foundation.background
|
||||||
import androidx.compose.foundation.clickable
|
import androidx.compose.foundation.clickable
|
||||||
import androidx.compose.foundation.layout.Arrangement
|
import androidx.compose.foundation.layout.Arrangement
|
||||||
@@ -39,6 +41,7 @@ import androidx.compose.foundation.layout.fillMaxSize
|
|||||||
import androidx.compose.foundation.layout.fillMaxWidth
|
import androidx.compose.foundation.layout.fillMaxWidth
|
||||||
import androidx.compose.foundation.layout.height
|
import androidx.compose.foundation.layout.height
|
||||||
import androidx.compose.foundation.layout.padding
|
import androidx.compose.foundation.layout.padding
|
||||||
|
import androidx.compose.foundation.layout.size
|
||||||
import androidx.compose.foundation.lazy.LazyColumn
|
import androidx.compose.foundation.lazy.LazyColumn
|
||||||
import androidx.compose.foundation.lazy.items
|
import androidx.compose.foundation.lazy.items
|
||||||
import androidx.compose.foundation.pager.HorizontalPager
|
import androidx.compose.foundation.pager.HorizontalPager
|
||||||
@@ -69,6 +72,7 @@ import androidx.compose.material3.MaterialTheme.colorScheme
|
|||||||
import androidx.compose.material3.MaterialTheme.typography
|
import androidx.compose.material3.MaterialTheme.typography
|
||||||
import androidx.compose.material3.OutlinedTextField
|
import androidx.compose.material3.OutlinedTextField
|
||||||
import androidx.compose.material3.PrimaryTabRow
|
import androidx.compose.material3.PrimaryTabRow
|
||||||
|
import androidx.compose.material3.RadioButton
|
||||||
import androidx.compose.material3.Scaffold
|
import androidx.compose.material3.Scaffold
|
||||||
import androidx.compose.material3.Slider
|
import androidx.compose.material3.Slider
|
||||||
import androidx.compose.material3.Tab
|
import androidx.compose.material3.Tab
|
||||||
@@ -86,6 +90,7 @@ import androidx.compose.runtime.getValue
|
|||||||
import androidx.compose.runtime.mutableFloatStateOf
|
import androidx.compose.runtime.mutableFloatStateOf
|
||||||
import androidx.compose.runtime.mutableIntStateOf
|
import androidx.compose.runtime.mutableIntStateOf
|
||||||
import androidx.compose.runtime.mutableStateListOf
|
import androidx.compose.runtime.mutableStateListOf
|
||||||
|
import androidx.compose.runtime.mutableStateMapOf
|
||||||
import androidx.compose.runtime.mutableStateOf
|
import androidx.compose.runtime.mutableStateOf
|
||||||
import androidx.compose.runtime.remember
|
import androidx.compose.runtime.remember
|
||||||
import androidx.compose.runtime.rememberCoroutineScope
|
import androidx.compose.runtime.rememberCoroutineScope
|
||||||
@@ -93,6 +98,7 @@ import androidx.compose.runtime.saveable.rememberSaveable
|
|||||||
import androidx.compose.runtime.setValue
|
import androidx.compose.runtime.setValue
|
||||||
import androidx.compose.ui.Alignment
|
import androidx.compose.ui.Alignment
|
||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
|
import androidx.compose.ui.draw.alpha
|
||||||
import androidx.compose.ui.draw.clip
|
import androidx.compose.ui.draw.clip
|
||||||
import androidx.compose.ui.platform.LocalContext
|
import androidx.compose.ui.platform.LocalContext
|
||||||
import androidx.compose.ui.platform.LocalFocusManager
|
import androidx.compose.ui.platform.LocalFocusManager
|
||||||
@@ -120,12 +126,14 @@ import com.bintianqi.owndroid.ui.FullWidthCheckBoxItem
|
|||||||
import com.bintianqi.owndroid.ui.FullWidthRadioButtonItem
|
import com.bintianqi.owndroid.ui.FullWidthRadioButtonItem
|
||||||
import com.bintianqi.owndroid.ui.FunctionItem
|
import com.bintianqi.owndroid.ui.FunctionItem
|
||||||
import com.bintianqi.owndroid.ui.ListItem
|
import com.bintianqi.owndroid.ui.ListItem
|
||||||
|
import com.bintianqi.owndroid.ui.MyLazyScaffold
|
||||||
import com.bintianqi.owndroid.ui.MyScaffold
|
import com.bintianqi.owndroid.ui.MyScaffold
|
||||||
import com.bintianqi.owndroid.ui.MySmallTitleScaffold
|
import com.bintianqi.owndroid.ui.MySmallTitleScaffold
|
||||||
import com.bintianqi.owndroid.ui.NavIcon
|
import com.bintianqi.owndroid.ui.NavIcon
|
||||||
import com.bintianqi.owndroid.ui.Notes
|
import com.bintianqi.owndroid.ui.Notes
|
||||||
import com.bintianqi.owndroid.ui.SwitchItem
|
import com.bintianqi.owndroid.ui.SwitchItem
|
||||||
import com.bintianqi.owndroid.yesOrNo
|
import com.bintianqi.owndroid.yesOrNo
|
||||||
|
import com.google.accompanist.drawablepainter.rememberDrawablePainter
|
||||||
import kotlinx.coroutines.channels.Channel
|
import kotlinx.coroutines.channels.Channel
|
||||||
import kotlinx.coroutines.delay
|
import kotlinx.coroutines.delay
|
||||||
import kotlinx.coroutines.flow.MutableStateFlow
|
import kotlinx.coroutines.flow.MutableStateFlow
|
||||||
@@ -153,6 +161,9 @@ fun SystemManagerScreen(
|
|||||||
FunctionItem(R.string.keyguard, icon = R.drawable.screen_lock_portrait_fill0) { onNavigate(Keyguard) }
|
FunctionItem(R.string.keyguard, icon = R.drawable.screen_lock_portrait_fill0) { onNavigate(Keyguard) }
|
||||||
if(VERSION.SDK_INT >= 24 && privilege.device && !privilege.dhizuku)
|
if(VERSION.SDK_INT >= 24 && privilege.device && !privilege.dhizuku)
|
||||||
FunctionItem(R.string.hardware_monitor, icon = R.drawable.memory_fill0) { onNavigate(HardwareMonitor) }
|
FunctionItem(R.string.hardware_monitor, icon = R.drawable.memory_fill0) { onNavigate(HardwareMonitor) }
|
||||||
|
FunctionItem(R.string.default_input_method, icon = R.drawable.keyboard_fill0) {
|
||||||
|
onNavigate(DefaultInputMethod)
|
||||||
|
}
|
||||||
if(VERSION.SDK_INT >= 24 && privilege.device) {
|
if(VERSION.SDK_INT >= 24 && privilege.device) {
|
||||||
FunctionItem(R.string.reboot, icon = R.drawable.restart_alt_fill0) { dialog = 1 }
|
FunctionItem(R.string.reboot, icon = R.drawable.restart_alt_fill0) { dialog = 1 }
|
||||||
}
|
}
|
||||||
@@ -314,17 +325,41 @@ data class SystemOptionsStatus(
|
|||||||
val btContactSharingDisabled: Boolean = false,
|
val btContactSharingDisabled: Boolean = false,
|
||||||
val commonCriteriaMode: Boolean = false,
|
val commonCriteriaMode: Boolean = false,
|
||||||
val usbSignalEnabled: Boolean = true,
|
val usbSignalEnabled: Boolean = true,
|
||||||
val canDisableUsbSignal: Boolean = true
|
val canDisableUsbSignal: Boolean = true,
|
||||||
|
val stayOnWhilePluggedIn: Boolean = false
|
||||||
)
|
)
|
||||||
|
|
||||||
@Serializable object SystemOptions
|
@Serializable object SystemOptions
|
||||||
|
|
||||||
|
class GlobalSetting(val icon: Int, val name: Int, val setting: String) // also for secure settings
|
||||||
|
|
||||||
|
// STAY_ON_WHILE_PLUGGED_IN is set separately
|
||||||
|
val globalSettings = listOf(
|
||||||
|
GlobalSetting(R.drawable.cell_tower_fill0, R.string.data_roaming, Settings.Global.DATA_ROAMING),
|
||||||
|
GlobalSetting(R.drawable.adb_fill0, R.string.enable_adb, Settings.Global.ADB_ENABLED),
|
||||||
|
GlobalSetting(R.drawable.usb_fill0, R.string.enable_usb_mass_storage,
|
||||||
|
Settings.Global.USB_MASS_STORAGE_ENABLED),
|
||||||
|
GlobalSetting(R.drawable.wifi_password_fill0, R.string.lockdown_admin_configured_network,
|
||||||
|
Settings.Global.WIFI_DEVICE_OWNER_CONFIGS_LOCKDOWN)
|
||||||
|
)
|
||||||
|
|
||||||
|
val secureSettings = listOf(
|
||||||
|
GlobalSetting(R.drawable.light_off_fill0, R.string.skip_first_use_hints,
|
||||||
|
Settings.Secure.SKIP_FIRST_USE_HINTS)
|
||||||
|
)
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
fun SystemOptionsScreen(vm: MyViewModel, onNavigateUp: () -> Unit) {
|
fun SystemOptionsScreen(vm: MyViewModel, onNavigateUp: () -> Unit) {
|
||||||
val privilege by Privilege.status.collectAsStateWithLifecycle()
|
val privilege by Privilege.status.collectAsStateWithLifecycle()
|
||||||
var dialog by rememberSaveable { mutableIntStateOf(0) }
|
var dialog by rememberSaveable { mutableIntStateOf(0) }
|
||||||
val status by vm.systemOptionsStatus.collectAsStateWithLifecycle()
|
val status by vm.systemOptionsStatus.collectAsStateWithLifecycle()
|
||||||
LaunchedEffect(Unit) { vm.getSystemOptionsStatus() }
|
val globalSettingsStatus = remember { mutableStateMapOf<String, Boolean>() }
|
||||||
|
val secureSettingsStatus = remember { mutableStateMapOf<String, Boolean>() }
|
||||||
|
LaunchedEffect(Unit) {
|
||||||
|
vm.getSystemOptionsStatus()
|
||||||
|
globalSettingsStatus.putAll(vm.getGlobalSettings())
|
||||||
|
secureSettingsStatus.putAll(vm.getSecureSettings())
|
||||||
|
}
|
||||||
MyScaffold(R.string.options, onNavigateUp, 0.dp) {
|
MyScaffold(R.string.options, onNavigateUp, 0.dp) {
|
||||||
SwitchItem(R.string.disable_cam, status.cameraDisabled, vm::setCameraDisabled,
|
SwitchItem(R.string.disable_cam, status.cameraDisabled, vm::setCameraDisabled,
|
||||||
R.drawable.no_photography_fill0)
|
R.drawable.no_photography_fill0)
|
||||||
@@ -366,6 +401,20 @@ fun SystemOptionsScreen(vm: MyViewModel, onNavigateUp: () -> Unit) {
|
|||||||
SwitchItem(R.string.enable_usb_signal, status.usbSignalEnabled,
|
SwitchItem(R.string.enable_usb_signal, status.usbSignalEnabled,
|
||||||
vm::setUsbSignalEnabled, R.drawable.usb_fill0)
|
vm::setUsbSignalEnabled, R.drawable.usb_fill0)
|
||||||
}
|
}
|
||||||
|
SwitchItem(R.string.stay_on_while_plugged_in, status.stayOnWhilePluggedIn,
|
||||||
|
vm::setStayOnWhilePluggedIn, R.drawable.mobile_phone_fill0)
|
||||||
|
globalSettings.forEach {
|
||||||
|
SwitchItem(it.name, globalSettingsStatus[it.setting] ?: false, { state ->
|
||||||
|
vm.setGlobalSetting(it.setting, state)
|
||||||
|
globalSettingsStatus[it.setting] = state
|
||||||
|
}, it.icon)
|
||||||
|
}
|
||||||
|
secureSettings.forEach {
|
||||||
|
SwitchItem(it.name, secureSettingsStatus[it.setting] ?: false, { state ->
|
||||||
|
vm.setSecureSetting(it.setting, state)
|
||||||
|
secureSettingsStatus[it.setting] = state
|
||||||
|
}, it.icon)
|
||||||
|
}
|
||||||
if (VERSION.SDK_INT < 34) {
|
if (VERSION.SDK_INT < 34) {
|
||||||
Row(
|
Row(
|
||||||
Modifier.fillMaxWidth().padding(horizontal = HorizontalPadding),
|
Modifier.fillMaxWidth().padding(horizontal = HorizontalPadding),
|
||||||
@@ -531,6 +580,47 @@ fun HardwareMonitorScreen(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Serializable object DefaultInputMethod
|
||||||
|
|
||||||
|
@Composable
|
||||||
|
fun DefaultInputMethodScreen(
|
||||||
|
getCurrentIm: () -> String, imListState: StateFlow<List<Pair<String, AppInfo>>>,
|
||||||
|
getImList: () -> Unit, setIm: (String) -> Unit, navigateUp: () -> Unit
|
||||||
|
) {
|
||||||
|
val context = LocalContext.current
|
||||||
|
val imList by imListState.collectAsStateWithLifecycle()
|
||||||
|
var selectedIm by remember { mutableStateOf("") }
|
||||||
|
LaunchedEffect(Unit) {
|
||||||
|
selectedIm = getCurrentIm()
|
||||||
|
getImList()
|
||||||
|
}
|
||||||
|
MyLazyScaffold(R.string.default_input_method, navigateUp) {
|
||||||
|
items(imList) { (id, info) ->
|
||||||
|
Row(
|
||||||
|
Modifier.fillMaxWidth().clickable { selectedIm = id }.padding(8.dp),
|
||||||
|
verticalAlignment = Alignment.CenterVertically
|
||||||
|
) {
|
||||||
|
RadioButton(selectedIm == id, { selectedIm = id })
|
||||||
|
Image(rememberDrawablePainter(info.icon), null, Modifier.size(40.dp))
|
||||||
|
Column(Modifier.padding(start = 8.dp)) {
|
||||||
|
Text(info.label)
|
||||||
|
Text(id, Modifier.alpha(0.7F), style = typography.bodyMedium)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
item {
|
||||||
|
Spacer(Modifier.height(8.dp))
|
||||||
|
Button({
|
||||||
|
setIm(selectedIm)
|
||||||
|
context.showOperationResultToast(true)
|
||||||
|
}, Modifier.fillMaxWidth().padding(horizontal = HorizontalPadding)) {
|
||||||
|
Text(stringResource(R.string.apply))
|
||||||
|
}
|
||||||
|
Spacer(Modifier.height(BottomPadding))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Serializable object ChangeTime
|
@Serializable object ChangeTime
|
||||||
|
|
||||||
@OptIn(ExperimentalMaterial3Api::class)
|
@OptIn(ExperimentalMaterial3Api::class)
|
||||||
|
|||||||
9
app/src/main/res/drawable/light_off_fill0.xml
Normal file
9
app/src/main/res/drawable/light_off_fill0.xml
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
android:width="24dp"
|
||||||
|
android:height="24dp"
|
||||||
|
android:viewportWidth="960"
|
||||||
|
android:viewportHeight="960">
|
||||||
|
<path
|
||||||
|
android:pathData="M423.5,856.5Q400,833 400,800h160q0,33 -23.5,56.5T480,880q-33,0 -56.5,-23.5ZM480,160q-44,0 -81.5,15.5T332,218l-58,-56q41,-38 93.5,-60T480,80q125,0 212.5,87.5T780,380q0,71 -25,121.5T698,584l-56,-56q21,-23 39.5,-59t18.5,-89q0,-92 -64,-156t-156,-64ZM848,848 L791,905 526,640L330,640q-69,-41 -109.5,-110T180,380q0,-20 2.5,-39t7.5,-37L56,168l56,-56 736,736ZM354,560h92L260,374v6q0,54 24.5,101t69.5,79ZM348,462ZM482,368ZM646,680v80L320,760v-80h326Z"
|
||||||
|
android:fillColor="#000000"/>
|
||||||
|
</vector>
|
||||||
@@ -134,6 +134,10 @@
|
|||||||
<string name="disable_bt_contact_share">禁止蓝牙分享联系人</string>
|
<string name="disable_bt_contact_share">禁止蓝牙分享联系人</string>
|
||||||
<string name="common_criteria_mode">通用标准模式</string>
|
<string name="common_criteria_mode">通用标准模式</string>
|
||||||
<string name="enable_usb_signal">启用USB信号</string>
|
<string name="enable_usb_signal">启用USB信号</string>
|
||||||
|
<string name="stay_on_while_plugged_in">充电时保持亮屏</string>
|
||||||
|
<string name="enable_adb">启用ADB</string>
|
||||||
|
<string name="enable_usb_mass_storage">启用USB大容量存储</string>
|
||||||
|
<string name="skip_first_use_hints">跳过首次使用提示</string>
|
||||||
<string name="keyguard">锁屏</string>
|
<string name="keyguard">锁屏</string>
|
||||||
<string name="lock_now">立即锁屏</string>
|
<string name="lock_now">立即锁屏</string>
|
||||||
<string name="lock_screen">锁屏</string>
|
<string name="lock_screen">锁屏</string>
|
||||||
@@ -148,7 +152,8 @@
|
|||||||
<string name="cpu_usages">CPU使用情况</string>
|
<string name="cpu_usages">CPU使用情况</string>
|
||||||
<string name="active">活动</string>
|
<string name="active">活动</string>
|
||||||
<string name="total">总计</string>
|
<string name="total">总计</string>
|
||||||
<string name="fan_speeds">Fan speeds</string>
|
<string name="fan_speeds">风扇速度</string>
|
||||||
|
<string name="default_input_method">默认输入法</string>
|
||||||
<string name="bug_report">错误报告</string>
|
<string name="bug_report">错误报告</string>
|
||||||
<string name="confirm_bug_report">请求错误报告?</string>
|
<string name="confirm_bug_report">请求错误报告?</string>
|
||||||
<string name="reboot">重启</string>
|
<string name="reboot">重启</string>
|
||||||
|
|||||||
@@ -143,6 +143,10 @@
|
|||||||
<string name="disable_bt_contact_share">Disable bluetooth contact sharing</string>
|
<string name="disable_bt_contact_share">Disable bluetooth contact sharing</string>
|
||||||
<string name="common_criteria_mode">Common criteria mode</string>
|
<string name="common_criteria_mode">Common criteria mode</string>
|
||||||
<string name="enable_usb_signal">Enable USB signal</string>
|
<string name="enable_usb_signal">Enable USB signal</string>
|
||||||
|
<string name="stay_on_while_plugged_in">Stay on while plugged in</string>
|
||||||
|
<string name="enable_adb">Enable ADB</string>
|
||||||
|
<string name="enable_usb_mass_storage">Enable USB mass storage</string>
|
||||||
|
<string name="skip_first_use_hints">Skip first use hints</string>
|
||||||
<string name="keyguard">Keyguard</string>
|
<string name="keyguard">Keyguard</string>
|
||||||
<string name="lock_now">Lock screen now</string>
|
<string name="lock_now">Lock screen now</string>
|
||||||
<string name="lock_screen">Lock screen</string>
|
<string name="lock_screen">Lock screen</string>
|
||||||
@@ -158,6 +162,7 @@
|
|||||||
<string name="active">Active</string>
|
<string name="active">Active</string>
|
||||||
<string name="total">Total</string>
|
<string name="total">Total</string>
|
||||||
<string name="fan_speeds">Fan speeds</string>
|
<string name="fan_speeds">Fan speeds</string>
|
||||||
|
<string name="default_input_method">Default input method</string>
|
||||||
<string name="bug_report">Bug report</string>
|
<string name="bug_report">Bug report</string>
|
||||||
<string name="confirm_bug_report">Request bug report?</string>
|
<string name="confirm_bug_report">Request bug report?</string>
|
||||||
<string name="reboot">Reboot</string>
|
<string name="reboot">Reboot</string>
|
||||||
|
|||||||
Reference in New Issue
Block a user