fix: 修复自定义主题切换并区分日夜配色
This commit is contained in:
@@ -213,6 +213,12 @@ object PreferKey {
|
||||
const val secondaryTextColor = "colorMD3OnPrimaryContainer"
|
||||
const val themeBackgroundColor = "colorMD3Background"
|
||||
const val labelContainerColor = "colorMD3SurfaceContainerLow"
|
||||
const val themeColorNight = "colorMD3PrimaryNight"
|
||||
const val secondaryThemeColorNight = "colorMD3SecondaryNight"
|
||||
const val primaryTextColorNight = "colorMD3OnSurfaceNight"
|
||||
const val secondaryTextColorNight = "colorMD3OnPrimaryContainerNight"
|
||||
const val themeBackgroundColorNight = "colorMD3BackgroundNight"
|
||||
const val labelContainerColorNight = "colorMD3SurfaceContainerLowNight"
|
||||
// 中间单线间隔设置
|
||||
const val enableItemDivider = "enableItemDivider"
|
||||
const val itemDividerWidth = "itemDividerWidth"
|
||||
|
||||
@@ -146,6 +146,12 @@ object ThemeImportExport {
|
||||
secondaryTextColor = ThemeConfig.secondaryTextColor,
|
||||
themeBackgroundColor = ThemeConfig.themeBackgroundColor,
|
||||
labelContainerColor = ThemeConfig.labelContainerColor,
|
||||
themeColorNight = ThemeConfig.themeColorNight,
|
||||
secondaryThemeColorNight = ThemeConfig.secondaryThemeColorNight,
|
||||
primaryTextColorNight = ThemeConfig.primaryTextColorNight,
|
||||
secondaryTextColorNight = ThemeConfig.secondaryTextColorNight,
|
||||
themeBackgroundColorNight = ThemeConfig.themeBackgroundColorNight,
|
||||
labelContainerColorNight = ThemeConfig.labelContainerColorNight,
|
||||
bookInfoInputColor = ThemeConfig.bookInfoInputColor,
|
||||
|
||||
// 容器设置
|
||||
@@ -317,6 +323,12 @@ object ThemeImportExport {
|
||||
ThemeConfig.secondaryTextColor = data.secondaryTextColor
|
||||
ThemeConfig.themeBackgroundColor = data.themeBackgroundColor
|
||||
ThemeConfig.labelContainerColor = data.labelContainerColor
|
||||
ThemeConfig.themeColorNight = data.themeColorNight
|
||||
ThemeConfig.secondaryThemeColorNight = data.secondaryThemeColorNight
|
||||
ThemeConfig.primaryTextColorNight = data.primaryTextColorNight
|
||||
ThemeConfig.secondaryTextColorNight = data.secondaryTextColorNight
|
||||
ThemeConfig.themeBackgroundColorNight = data.themeBackgroundColorNight
|
||||
ThemeConfig.labelContainerColorNight = data.labelContainerColorNight
|
||||
ThemeConfig.bookInfoInputColor = data.bookInfoInputColor
|
||||
|
||||
// 容器设置
|
||||
@@ -556,6 +568,12 @@ data class ThemeExportData(
|
||||
val secondaryTextColor: Int = 0,
|
||||
val themeBackgroundColor: Int = 0,
|
||||
val labelContainerColor: Int = 0,
|
||||
val themeColorNight: Int = 0,
|
||||
val secondaryThemeColorNight: Int = 0,
|
||||
val primaryTextColorNight: Int = 0,
|
||||
val secondaryTextColorNight: Int = 0,
|
||||
val themeBackgroundColorNight: Int = 0,
|
||||
val labelContainerColorNight: Int = 0,
|
||||
val bookInfoInputColor: Int = 0,
|
||||
|
||||
// 容器设置
|
||||
|
||||
@@ -91,6 +91,8 @@ object BackupConfig {
|
||||
PreferKey.bgImageNBlurring,
|
||||
PreferKey.themeColor,
|
||||
PreferKey.secondaryThemeColor,
|
||||
PreferKey.themeColorNight,
|
||||
PreferKey.secondaryThemeColorNight,
|
||||
PreferKey.paletteStyle,
|
||||
PreferKey.materialVersion,
|
||||
PreferKey.composeEngine,
|
||||
@@ -116,7 +118,11 @@ object BackupConfig {
|
||||
PreferKey.primaryTextColor,
|
||||
PreferKey.secondaryTextColor,
|
||||
PreferKey.themeBackgroundColor,
|
||||
PreferKey.labelContainerColor
|
||||
PreferKey.labelContainerColor,
|
||||
PreferKey.primaryTextColorNight,
|
||||
PreferKey.secondaryTextColorNight,
|
||||
PreferKey.themeBackgroundColorNight,
|
||||
PreferKey.labelContainerColorNight
|
||||
)
|
||||
|
||||
private val coverPrefKeys = arrayOf(
|
||||
@@ -165,4 +171,4 @@ object BackupConfig {
|
||||
FileUtils.createFileIfNotExist(ignoreConfigPath).writeText(json)
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -59,6 +59,12 @@ fun CustomThemeScreen(
|
||||
val secondaryTextColor = ThemeConfig.secondaryTextColor
|
||||
val themeBackgroundColor = ThemeConfig.themeBackgroundColor
|
||||
val labelContainerColor = ThemeConfig.labelContainerColor
|
||||
val themeColorNight = ThemeConfig.themeColorNight
|
||||
val secondaryThemeColorNight = ThemeConfig.secondaryThemeColorNight
|
||||
val primaryTextColorNight = ThemeConfig.primaryTextColorNight
|
||||
val secondaryTextColorNight = ThemeConfig.secondaryTextColorNight
|
||||
val themeBackgroundColorNight = ThemeConfig.themeBackgroundColorNight
|
||||
val labelContainerColorNight = ThemeConfig.labelContainerColorNight
|
||||
|
||||
val primaryColor = MaterialTheme.colorScheme.primary
|
||||
|
||||
@@ -101,153 +107,37 @@ fun CustomThemeScreen(
|
||||
// Color settings vs Seed color toggle based on enableDeepPersonalization
|
||||
if (enableDeepPersonalization) {
|
||||
item {
|
||||
SplicedColumnGroup(title = stringResource(R.string.color_setting)) {
|
||||
// Primary colors
|
||||
ClickableSettingItem(
|
||||
title = stringResource(R.string.theme_manage_primary_color),
|
||||
option = if (themeColor != 0) "#${Integer.toHexString(themeColor).uppercase()}" else stringResource(R.string.click_to_select),
|
||||
onClick = {
|
||||
currentColorKey = "themeColor"
|
||||
CustomColorSettings(
|
||||
title = stringResource(R.string.day),
|
||||
primary = themeColor,
|
||||
secondary = secondaryThemeColor,
|
||||
primaryText = primaryTextColor,
|
||||
secondaryText = secondaryTextColor,
|
||||
background = themeBackgroundColor,
|
||||
labelContainer = labelContainerColor,
|
||||
keySuffix = "",
|
||||
onSelect = {
|
||||
currentColorKey = it
|
||||
showColorPicker = true
|
||||
},
|
||||
)
|
||||
}
|
||||
item {
|
||||
CustomColorSettings(
|
||||
title = stringResource(R.string.night),
|
||||
primary = themeColorNight,
|
||||
secondary = secondaryThemeColorNight,
|
||||
primaryText = primaryTextColorNight,
|
||||
secondaryText = secondaryTextColorNight,
|
||||
background = themeBackgroundColorNight,
|
||||
labelContainer = labelContainerColorNight,
|
||||
keySuffix = "Night",
|
||||
onSelect = {
|
||||
currentColorKey = it
|
||||
showColorPicker = true
|
||||
},
|
||||
trailingContent = {
|
||||
if (themeColor != 0) {
|
||||
Box(
|
||||
modifier = Modifier
|
||||
.size(28.dp)
|
||||
.clip(CircleShape)
|
||||
.background(Color(themeColor))
|
||||
.border(
|
||||
1.dp,
|
||||
MaterialTheme.colorScheme.outlineVariant,
|
||||
CircleShape
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
ClickableSettingItem(
|
||||
title = stringResource(R.string.theme_manage_secondary_color),
|
||||
option = if (secondaryThemeColor != 0) "#${Integer.toHexString(secondaryThemeColor).uppercase()}" else stringResource(R.string.click_to_select),
|
||||
onClick = {
|
||||
currentColorKey = "secondaryThemeColor"
|
||||
showColorPicker = true
|
||||
},
|
||||
trailingContent = {
|
||||
if (secondaryThemeColor != 0) {
|
||||
Box(
|
||||
modifier = Modifier
|
||||
.size(28.dp)
|
||||
.clip(CircleShape)
|
||||
.background(Color(secondaryThemeColor))
|
||||
.border(
|
||||
1.dp,
|
||||
MaterialTheme.colorScheme.outlineVariant,
|
||||
CircleShape
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
ClickableSettingItem(
|
||||
title = stringResource(R.string.theme_manage_primary_text_color),
|
||||
option = if (primaryTextColor != 0) "#${Integer.toHexString(primaryTextColor).uppercase()}" else stringResource(R.string.click_to_select),
|
||||
onClick = {
|
||||
currentColorKey = "primaryTextColor"
|
||||
showColorPicker = true
|
||||
},
|
||||
trailingContent = {
|
||||
if (primaryTextColor != 0) {
|
||||
Box(
|
||||
modifier = Modifier
|
||||
.size(28.dp)
|
||||
.clip(CircleShape)
|
||||
.background(Color(primaryTextColor))
|
||||
.border(
|
||||
1.dp,
|
||||
MaterialTheme.colorScheme.outlineVariant,
|
||||
CircleShape
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
ClickableSettingItem(
|
||||
title = stringResource(R.string.theme_manage_secondary_text_color),
|
||||
option = if (secondaryTextColor != 0) "#${Integer.toHexString(secondaryTextColor).uppercase()}" else stringResource(R.string.click_to_select),
|
||||
onClick = {
|
||||
currentColorKey = "secondaryTextColor"
|
||||
showColorPicker = true
|
||||
},
|
||||
trailingContent = {
|
||||
if (secondaryTextColor != 0) {
|
||||
Box(
|
||||
modifier = Modifier
|
||||
.size(28.dp)
|
||||
.clip(CircleShape)
|
||||
.background(Color(secondaryTextColor))
|
||||
.border(
|
||||
1.dp,
|
||||
MaterialTheme.colorScheme.outlineVariant,
|
||||
CircleShape
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
ClickableSettingItem(
|
||||
title = stringResource(R.string.theme_manage_background_color),
|
||||
option = if (themeBackgroundColor != 0) "#${Integer.toHexString(themeBackgroundColor).uppercase()}" else stringResource(R.string.click_to_select),
|
||||
onClick = {
|
||||
currentColorKey = "themeBackgroundColor"
|
||||
showColorPicker = true
|
||||
},
|
||||
trailingContent = {
|
||||
if (themeBackgroundColor != 0) {
|
||||
Box(
|
||||
modifier = Modifier
|
||||
.size(28.dp)
|
||||
.clip(CircleShape)
|
||||
.background(Color(themeBackgroundColor))
|
||||
.border(
|
||||
1.dp,
|
||||
MaterialTheme.colorScheme.outlineVariant,
|
||||
CircleShape
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
ClickableSettingItem(
|
||||
title = stringResource(R.string.theme_manage_label_container_color),
|
||||
option = if (labelContainerColor != 0) "#${Integer.toHexString(labelContainerColor).uppercase()}" else stringResource(R.string.click_to_select),
|
||||
onClick = {
|
||||
currentColorKey = "labelContainerColor"
|
||||
showColorPicker = true
|
||||
},
|
||||
trailingContent = {
|
||||
if (labelContainerColor != 0) {
|
||||
Box(
|
||||
modifier = Modifier
|
||||
.size(28.dp)
|
||||
.clip(CircleShape)
|
||||
.background(Color(labelContainerColor))
|
||||
.border(
|
||||
1.dp,
|
||||
MaterialTheme.colorScheme.outlineVariant,
|
||||
CircleShape
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
} else {
|
||||
item {
|
||||
SplicedColumnGroup(title = stringResource(R.string.custom_theme)) {
|
||||
@@ -310,6 +200,12 @@ fun CustomThemeScreen(
|
||||
"secondaryTextColor" -> secondaryTextColor
|
||||
"themeBackgroundColor" -> themeBackgroundColor
|
||||
"labelContainerColor" -> labelContainerColor
|
||||
"themeColorNight" -> themeColorNight
|
||||
"secondaryThemeColorNight" -> secondaryThemeColorNight
|
||||
"primaryTextColorNight" -> primaryTextColorNight
|
||||
"secondaryTextColorNight" -> secondaryTextColorNight
|
||||
"themeBackgroundColorNight" -> themeBackgroundColorNight
|
||||
"labelContainerColorNight" -> labelContainerColorNight
|
||||
else -> 0
|
||||
},
|
||||
onDismissRequest = { showColorPicker = false },
|
||||
@@ -321,6 +217,12 @@ fun CustomThemeScreen(
|
||||
"secondaryTextColor" -> ThemeConfig.secondaryTextColor = it
|
||||
"themeBackgroundColor" -> ThemeConfig.themeBackgroundColor = it
|
||||
"labelContainerColor" -> ThemeConfig.labelContainerColor = it
|
||||
"themeColorNight" -> ThemeConfig.themeColorNight = it
|
||||
"secondaryThemeColorNight" -> ThemeConfig.secondaryThemeColorNight = it
|
||||
"primaryTextColorNight" -> ThemeConfig.primaryTextColorNight = it
|
||||
"secondaryTextColorNight" -> ThemeConfig.secondaryTextColorNight = it
|
||||
"themeBackgroundColorNight" -> ThemeConfig.themeBackgroundColorNight = it
|
||||
"labelContainerColorNight" -> ThemeConfig.labelContainerColorNight = it
|
||||
}
|
||||
}
|
||||
)
|
||||
@@ -357,6 +259,66 @@ fun CustomThemeScreen(
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun CustomColorSettings(
|
||||
title: String,
|
||||
primary: Int,
|
||||
secondary: Int,
|
||||
primaryText: Int,
|
||||
secondaryText: Int,
|
||||
background: Int,
|
||||
labelContainer: Int,
|
||||
keySuffix: String,
|
||||
onSelect: (String) -> Unit,
|
||||
) {
|
||||
SplicedColumnGroup(title = title) {
|
||||
CustomColorSettingItem(
|
||||
title = stringResource(R.string.theme_manage_primary_color),
|
||||
colorValue = primary,
|
||||
onClick = { onSelect("themeColor$keySuffix") },
|
||||
)
|
||||
CustomColorSettingItem(
|
||||
title = stringResource(R.string.theme_manage_secondary_color),
|
||||
colorValue = secondary,
|
||||
onClick = { onSelect("secondaryThemeColor$keySuffix") },
|
||||
)
|
||||
CustomColorSettingItem(
|
||||
title = stringResource(R.string.theme_manage_primary_text_color),
|
||||
colorValue = primaryText,
|
||||
onClick = { onSelect("primaryTextColor$keySuffix") },
|
||||
)
|
||||
CustomColorSettingItem(
|
||||
title = stringResource(R.string.theme_manage_secondary_text_color),
|
||||
colorValue = secondaryText,
|
||||
onClick = { onSelect("secondaryTextColor$keySuffix") },
|
||||
)
|
||||
CustomColorSettingItem(
|
||||
title = stringResource(R.string.theme_manage_background_color),
|
||||
colorValue = background,
|
||||
onClick = { onSelect("themeBackgroundColor$keySuffix") },
|
||||
)
|
||||
CustomColorSettingItem(
|
||||
title = stringResource(R.string.theme_manage_label_container_color),
|
||||
colorValue = labelContainer,
|
||||
onClick = { onSelect("labelContainerColor$keySuffix") },
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun CustomColorSettingItem(
|
||||
title: String,
|
||||
colorValue: Int,
|
||||
onClick: () -> Unit,
|
||||
) {
|
||||
ClickableSettingItem(
|
||||
title = title,
|
||||
option = formatColorOption(colorValue) ?: stringResource(R.string.click_to_select),
|
||||
onClick = onClick,
|
||||
trailingContent = { ColorSwatch(colorValue) },
|
||||
)
|
||||
}
|
||||
|
||||
private fun formatColorOption(colorValue: Int): String? {
|
||||
if (colorValue == 0) return null
|
||||
return "#${Integer.toHexString(colorValue).uppercase()}"
|
||||
|
||||
@@ -14,8 +14,27 @@ data class TagColorPair(
|
||||
val bgColor: Int = 0
|
||||
)
|
||||
|
||||
data class CustomThemeColors(
|
||||
val primary: Int,
|
||||
val secondary: Int,
|
||||
val primaryText: Int,
|
||||
val secondaryText: Int,
|
||||
val background: Int,
|
||||
val labelContainer: Int,
|
||||
) {
|
||||
val hasCustomColor: Boolean
|
||||
get() = primary != 0 ||
|
||||
secondary != 0 ||
|
||||
primaryText != 0 ||
|
||||
secondaryText != 0 ||
|
||||
background != 0 ||
|
||||
labelContainer != 0
|
||||
}
|
||||
|
||||
object ThemeConfig {
|
||||
|
||||
private const val CUSTOM_APP_THEME = "12"
|
||||
|
||||
var containerOpacity by prefDelegate(PreferKey.containerOpacity, 100)
|
||||
|
||||
var topBarOpacity by prefDelegate(PreferKey.topBarOpacity, 100)
|
||||
@@ -105,6 +124,42 @@ object ThemeConfig {
|
||||
|
||||
var labelContainerColor by prefDelegate(PreferKey.labelContainerColor, 0)
|
||||
|
||||
var themeColorNight by prefDelegate(PreferKey.themeColorNight, 0)
|
||||
|
||||
var secondaryThemeColorNight by prefDelegate(PreferKey.secondaryThemeColorNight, 0)
|
||||
|
||||
var primaryTextColorNight by prefDelegate(PreferKey.primaryTextColorNight, 0)
|
||||
|
||||
var secondaryTextColorNight by prefDelegate(PreferKey.secondaryTextColorNight, 0)
|
||||
|
||||
var themeBackgroundColorNight by prefDelegate(PreferKey.themeBackgroundColorNight, 0)
|
||||
|
||||
var labelContainerColorNight by prefDelegate(PreferKey.labelContainerColorNight, 0)
|
||||
|
||||
val isDeepPersonalizationActive: Boolean
|
||||
get() = appTheme == CUSTOM_APP_THEME && enableDeepPersonalization
|
||||
|
||||
fun customThemeColors(isDark: Boolean): CustomThemeColors {
|
||||
if (!isDark) {
|
||||
return CustomThemeColors(
|
||||
primary = themeColor,
|
||||
secondary = secondaryThemeColor,
|
||||
primaryText = primaryTextColor,
|
||||
secondaryText = secondaryTextColor,
|
||||
background = themeBackgroundColor,
|
||||
labelContainer = labelContainerColor,
|
||||
)
|
||||
}
|
||||
return CustomThemeColors(
|
||||
primary = themeColorNight.takeIf { it != 0 } ?: themeColor,
|
||||
secondary = secondaryThemeColorNight.takeIf { it != 0 } ?: secondaryThemeColor,
|
||||
primaryText = primaryTextColorNight.takeIf { it != 0 } ?: primaryTextColor,
|
||||
secondaryText = secondaryTextColorNight.takeIf { it != 0 } ?: secondaryTextColor,
|
||||
background = themeBackgroundColorNight.takeIf { it != 0 } ?: themeBackgroundColor,
|
||||
labelContainer = labelContainerColorNight.takeIf { it != 0 } ?: labelContainerColor,
|
||||
)
|
||||
}
|
||||
|
||||
var enableItemDivider by prefDelegate(PreferKey.enableItemDivider, false)
|
||||
|
||||
var itemDividerWidth by prefDelegate(PreferKey.itemDividerWidth, 1f)
|
||||
|
||||
@@ -132,6 +132,7 @@ fun EditThemeSheet(
|
||||
onCheckedChange = { data = data.copy(enableDeepPersonalization = !it) }
|
||||
)
|
||||
if (data.enableDeepPersonalization) {
|
||||
SectionTitle(stringResource(R.string.day))
|
||||
ColorItem(stringResource(R.string.theme_manage_primary_color), data.themeColor) {
|
||||
currentColorKey = "themeColor"; showColorPicker = true
|
||||
}
|
||||
@@ -150,6 +151,25 @@ fun EditThemeSheet(
|
||||
ColorItem(stringResource(R.string.theme_manage_label_container_color), data.labelContainerColor) {
|
||||
currentColorKey = "labelContainerColor"; showColorPicker = true
|
||||
}
|
||||
SectionTitle(stringResource(R.string.night))
|
||||
ColorItem(stringResource(R.string.theme_manage_primary_color), data.themeColorNight) {
|
||||
currentColorKey = "themeColorNight"; showColorPicker = true
|
||||
}
|
||||
ColorItem(stringResource(R.string.theme_manage_secondary_color), data.secondaryThemeColorNight) {
|
||||
currentColorKey = "secondaryThemeColorNight"; showColorPicker = true
|
||||
}
|
||||
ColorItem(stringResource(R.string.theme_manage_primary_text_color), data.primaryTextColorNight) {
|
||||
currentColorKey = "primaryTextColorNight"; showColorPicker = true
|
||||
}
|
||||
ColorItem(stringResource(R.string.theme_manage_secondary_text_color), data.secondaryTextColorNight) {
|
||||
currentColorKey = "secondaryTextColorNight"; showColorPicker = true
|
||||
}
|
||||
ColorItem(stringResource(R.string.theme_manage_background_color), data.themeBackgroundColorNight) {
|
||||
currentColorKey = "themeBackgroundColorNight"; showColorPicker = true
|
||||
}
|
||||
ColorItem(stringResource(R.string.theme_manage_label_container_color), data.labelContainerColorNight) {
|
||||
currentColorKey = "labelContainerColorNight"; showColorPicker = true
|
||||
}
|
||||
} else {
|
||||
ColorItem(stringResource(R.string.theme_manage_day_seed_color), data.cPrimary) {
|
||||
currentColorKey = "cPrimary"; showColorPicker = true
|
||||
@@ -310,6 +330,12 @@ fun EditThemeSheet(
|
||||
"secondaryTextColor" -> data.secondaryTextColor
|
||||
"themeBackgroundColor" -> data.themeBackgroundColor
|
||||
"labelContainerColor" -> data.labelContainerColor
|
||||
"themeColorNight" -> data.themeColorNight
|
||||
"secondaryThemeColorNight" -> data.secondaryThemeColorNight
|
||||
"primaryTextColorNight" -> data.primaryTextColorNight
|
||||
"secondaryTextColorNight" -> data.secondaryTextColorNight
|
||||
"themeBackgroundColorNight" -> data.themeBackgroundColorNight
|
||||
"labelContainerColorNight" -> data.labelContainerColorNight
|
||||
"cPrimary" -> data.cPrimary
|
||||
"cNPrimary" -> data.cNPrimary
|
||||
else -> 0
|
||||
@@ -323,6 +349,12 @@ fun EditThemeSheet(
|
||||
"secondaryTextColor" -> data.copy(secondaryTextColor = color)
|
||||
"themeBackgroundColor" -> data.copy(themeBackgroundColor = color)
|
||||
"labelContainerColor" -> data.copy(labelContainerColor = color)
|
||||
"themeColorNight" -> data.copy(themeColorNight = color)
|
||||
"secondaryThemeColorNight" -> data.copy(secondaryThemeColorNight = color)
|
||||
"primaryTextColorNight" -> data.copy(primaryTextColorNight = color)
|
||||
"secondaryTextColorNight" -> data.copy(secondaryTextColorNight = color)
|
||||
"themeBackgroundColorNight" -> data.copy(themeBackgroundColorNight = color)
|
||||
"labelContainerColorNight" -> data.copy(labelContainerColorNight = color)
|
||||
"cPrimary" -> data.copy(cPrimary = color)
|
||||
"cNPrimary" -> data.copy(cNPrimary = color)
|
||||
else -> data
|
||||
|
||||
@@ -301,13 +301,28 @@ private fun SavedThemeItem(
|
||||
else if (theme.data.cPrimary != 0) Color(theme.data.cPrimary)
|
||||
else MaterialTheme.colorScheme.primary
|
||||
|
||||
val darkPrimary = if (theme.data.cNPrimary != 0) Color(theme.data.cNPrimary)
|
||||
else lightPrimary
|
||||
val darkPrimary = if (theme.data.themeColorNight != 0) {
|
||||
Color(theme.data.themeColorNight)
|
||||
} else if (theme.data.cNPrimary != 0) {
|
||||
Color(theme.data.cNPrimary)
|
||||
} else {
|
||||
lightPrimary
|
||||
}
|
||||
|
||||
val lightBg = if (theme.data.themeBackgroundColor != 0) Color(theme.data.themeBackgroundColor)
|
||||
else Color(0xFFF7F2FA)
|
||||
|
||||
val darkBg = if (theme.data.isPureBlack) Color.Black else Color(0xFF1C1B1F)
|
||||
val darkBg = if (theme.data.themeBackgroundColorNight != 0) {
|
||||
Color(theme.data.themeBackgroundColorNight)
|
||||
} else if (theme.data.enableDeepPersonalization &&
|
||||
theme.data.themeBackgroundColor != 0
|
||||
) {
|
||||
Color(theme.data.themeBackgroundColor)
|
||||
} else if (theme.data.isPureBlack) {
|
||||
Color.Black
|
||||
} else {
|
||||
Color(0xFF1C1B1F)
|
||||
}
|
||||
|
||||
// 预览区域
|
||||
Column(
|
||||
@@ -357,7 +372,15 @@ private fun SavedThemeItem(
|
||||
AppText(
|
||||
text = stringResource(R.string.theme_manage_preview_night),
|
||||
style = MaterialTheme.typography.labelMediumEmphasized,
|
||||
color = Color.White.copy(alpha = 0.5f),
|
||||
color = if (theme.data.primaryTextColorNight != 0) {
|
||||
Color(theme.data.primaryTextColorNight).copy(alpha = 0.6f)
|
||||
} else if (theme.data.enableDeepPersonalization &&
|
||||
theme.data.primaryTextColor != 0
|
||||
) {
|
||||
Color(theme.data.primaryTextColor).copy(alpha = 0.6f)
|
||||
} else {
|
||||
Color.White.copy(alpha = 0.5f)
|
||||
},
|
||||
modifier = Modifier
|
||||
.align(Alignment.CenterStart)
|
||||
.padding(start = 12.dp)
|
||||
|
||||
@@ -79,6 +79,7 @@ import io.legado.app.ui.main.home.HomeRouteScreen
|
||||
import io.legado.app.ui.main.my.MyScreen
|
||||
import io.legado.app.ui.main.my.PrefClickEvent
|
||||
import io.legado.app.ui.main.rss.RssScreen
|
||||
import io.legado.app.ui.theme.LegadoTheme
|
||||
import io.legado.app.ui.widget.components.AppScaffold
|
||||
import io.legado.app.ui.widget.components.FloatingBottomBar
|
||||
import io.legado.app.ui.widget.components.FloatingBottomBarItem
|
||||
@@ -172,8 +173,9 @@ fun MainScreen(
|
||||
}
|
||||
|
||||
val hazeState = remember { HazeState() }
|
||||
val floatingBarSurfaceColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
val customSecondaryColor = ThemeConfig.customThemeColors(LegadoTheme.isDark).secondary
|
||||
val floatingBarSurfaceColor = if (ThemeConfig.isDeepPersonalizationActive && customSecondaryColor != 0) {
|
||||
Color(customSecondaryColor)
|
||||
} else {
|
||||
MaterialTheme.colorScheme.surface
|
||||
}
|
||||
|
||||
@@ -35,12 +35,7 @@ fun AppTheme(
|
||||
|
||||
// 2. 深度个性化配置
|
||||
val enableDeepPersonalization = ThemeConfig.enableDeepPersonalization
|
||||
val themeColor = ThemeConfig.themeColor
|
||||
val secondaryThemeColor = ThemeConfig.secondaryThemeColor
|
||||
val primaryTextColor = ThemeConfig.primaryTextColor
|
||||
val secondaryTextColor = ThemeConfig.secondaryTextColor
|
||||
val themeBackgroundColor = ThemeConfig.themeBackgroundColor
|
||||
val customLabelContainerColor = ThemeConfig.labelContainerColor
|
||||
val customColors = ThemeConfig.customThemeColors(effectiveDarkTheme)
|
||||
|
||||
// 3. 加载自定义字体
|
||||
val customFontFamily = rememberCustomFont(appFontPath)
|
||||
@@ -48,20 +43,20 @@ fun AppTheme(
|
||||
// 4. 解析配色方案 (Material 3 ColorScheme)
|
||||
val colorScheme = remember(
|
||||
context, appThemeMode, effectiveDarkTheme, isPureBlack, customPrimary, customNightPrimary,
|
||||
enableDeepPersonalization, themeColor, secondaryThemeColor, primaryTextColor,
|
||||
secondaryTextColor, themeBackgroundColor, customLabelContainerColor,
|
||||
enableDeepPersonalization, customColors,
|
||||
paletteStyleValue, materialVersion
|
||||
) {
|
||||
if (enableDeepPersonalization &&
|
||||
(themeColor != 0 || secondaryThemeColor != 0 || primaryTextColor != 0 ||
|
||||
secondaryTextColor != 0 || themeBackgroundColor != 0 || customLabelContainerColor != 0)) {
|
||||
if (appThemeMode == AppThemeMode.Custom &&
|
||||
enableDeepPersonalization &&
|
||||
customColors.hasCustomColor
|
||||
) {
|
||||
val userPalette = UserColorPalette(
|
||||
primaryColor = if (themeColor != 0) Color(themeColor) else Color(0xFF6750A4),
|
||||
secondaryColor = if (secondaryThemeColor != 0) Color(secondaryThemeColor) else Color(0xFF625B71),
|
||||
backgroundColor = if (themeBackgroundColor != 0) Color(themeBackgroundColor) else Color(0xFFFEF7FF),
|
||||
primaryFontColor = if (primaryTextColor != 0) Color(primaryTextColor) else Color(0xFF1C1B1F),
|
||||
secondaryFontColor = if (secondaryTextColor != 0) Color(secondaryTextColor) else Color(0xFF49454F),
|
||||
labelContainerColor = if (customLabelContainerColor != 0) Color(customLabelContainerColor) else Color(0xFFF7F2FA)
|
||||
primaryColor = if (customColors.primary != 0) Color(customColors.primary) else Color(0xFF6750A4),
|
||||
secondaryColor = if (customColors.secondary != 0) Color(customColors.secondary) else Color(0xFF625B71),
|
||||
backgroundColor = if (customColors.background != 0) Color(customColors.background) else Color(0xFFFEF7FF),
|
||||
primaryFontColor = if (customColors.primaryText != 0) Color(customColors.primaryText) else Color(0xFF1C1B1F),
|
||||
secondaryFontColor = if (customColors.secondaryText != 0) Color(customColors.secondaryText) else Color(0xFF49454F),
|
||||
labelContainerColor = if (customColors.labelContainer != 0) Color(customColors.labelContainer) else Color(0xFFF7F2FA)
|
||||
)
|
||||
generateColorScheme(userPalette, effectiveDarkTheme)
|
||||
} else {
|
||||
|
||||
@@ -108,14 +108,20 @@ fun MiuixThemeWrapper(
|
||||
}
|
||||
|
||||
val miuixColorScheme = MiuixTheme.colorScheme
|
||||
val mappedColorScheme = remember(miuixColorScheme) {
|
||||
val customBgColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.themeBackgroundColor != 0) {
|
||||
Color(ThemeConfig.themeBackgroundColor)
|
||||
val customColors = ThemeConfig.customThemeColors(darkTheme)
|
||||
val isDeepPersonalizationActive = ThemeConfig.isDeepPersonalizationActive
|
||||
val mappedColorScheme = remember(
|
||||
miuixColorScheme,
|
||||
customColors,
|
||||
isDeepPersonalizationActive,
|
||||
) {
|
||||
val customBgColor = if (isDeepPersonalizationActive && customColors.background != 0) {
|
||||
Color(customColors.background)
|
||||
} else {
|
||||
miuixColorScheme.background
|
||||
}
|
||||
val customFontColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.primaryTextColor != 0) {
|
||||
Color(ThemeConfig.primaryTextColor)
|
||||
val customFontColor = if (isDeepPersonalizationActive && customColors.primaryText != 0) {
|
||||
Color(customColors.primaryText)
|
||||
} else {
|
||||
miuixColorScheme.onSurface
|
||||
}
|
||||
@@ -237,20 +243,9 @@ fun MaterialThemeWrapper(
|
||||
materialTypography.toLegadoTypography().withFont(customFontFamily)
|
||||
}
|
||||
val semanticColors = remember(colorScheme) {
|
||||
val customBgColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.themeBackgroundColor != 0) {
|
||||
Color(ThemeConfig.themeBackgroundColor)
|
||||
} else {
|
||||
colorScheme.background
|
||||
}
|
||||
val customFontColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.primaryTextColor != 0) {
|
||||
Color(ThemeConfig.primaryTextColor)
|
||||
} else {
|
||||
colorScheme.onSurface
|
||||
}
|
||||
|
||||
colorScheme.toLegadoColorScheme(
|
||||
customBgColor = customBgColor,
|
||||
customFontColor = customFontColor,
|
||||
customBgColor = colorScheme.background,
|
||||
customFontColor = colorScheme.onSurface,
|
||||
customTopBarColor = colorScheme.surface,
|
||||
customNavBarColor = colorScheme.surface
|
||||
)
|
||||
|
||||
@@ -130,13 +130,14 @@ fun FloatingBottomBar(
|
||||
content: @Composable RowScope.() -> Unit
|
||||
) {
|
||||
val isInLightTheme = !LegadoTheme.isDark
|
||||
val accentColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.themeColor != 0) {
|
||||
Color(ThemeConfig.themeColor)
|
||||
val customColors = ThemeConfig.customThemeColors(LegadoTheme.isDark)
|
||||
val accentColor = if (ThemeConfig.isDeepPersonalizationActive && customColors.primary != 0) {
|
||||
Color(customColors.primary)
|
||||
} else {
|
||||
LegadoTheme.colorScheme.primary
|
||||
}
|
||||
val containerColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor).copy(alpha = if (isBlurEnabled) ThemeConfig.bottomBarBlurAlpha / 100f else 1f)
|
||||
val containerColor = if (ThemeConfig.isDeepPersonalizationActive && customColors.secondary != 0) {
|
||||
Color(customColors.secondary).copy(alpha = if (isBlurEnabled) ThemeConfig.bottomBarBlurAlpha / 100f else 1f)
|
||||
} else if (isBlurEnabled) {
|
||||
LegadoTheme.colorScheme.surfaceContainer.copy(alpha = ThemeConfig.bottomBarBlurAlpha / 100f)
|
||||
} else {
|
||||
|
||||
@@ -3,6 +3,7 @@ package io.legado.app.ui.widget.components
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import io.legado.app.ui.config.themeConfig.ThemeConfig
|
||||
import io.legado.app.ui.theme.LegadoTheme
|
||||
|
||||
object GlassDefaults {
|
||||
|
||||
@@ -22,8 +23,9 @@ object GlassDefaults {
|
||||
|
||||
@Composable
|
||||
fun secondaryColorOr(fallback: @Composable () -> Color): Color {
|
||||
return if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
val secondaryColor = ThemeConfig.customThemeColors(LegadoTheme.isDark).secondary
|
||||
return if (ThemeConfig.isDeepPersonalizationActive && secondaryColor != 0) {
|
||||
Color(secondaryColor)
|
||||
} else {
|
||||
fallback()
|
||||
}
|
||||
|
||||
@@ -50,6 +50,7 @@ fun AppNavigationBar(
|
||||
else -> NavigationBarDisplayMode.IconWithSelectedLabel
|
||||
}
|
||||
val opacity = (ThemeConfig.bottomBarOpacity.coerceIn(0, 100)) / 100f
|
||||
val customSecondaryColor = ThemeConfig.customThemeColors(LegadoTheme.isDark).secondary
|
||||
val hazeState = LocalHazeState.current
|
||||
val hazeModifier = if (hazeState != null) {
|
||||
Modifier.regularHazeEffect(hazeState)
|
||||
@@ -59,8 +60,8 @@ fun AppNavigationBar(
|
||||
|
||||
if (isMiuix) {
|
||||
val baseColor =
|
||||
if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
if (ThemeConfig.isDeepPersonalizationActive && customSecondaryColor != 0) {
|
||||
Color(customSecondaryColor)
|
||||
} else {
|
||||
GlassDefaults.glassColor(
|
||||
noBlurColor = MiuixTheme.colorScheme.surface,
|
||||
@@ -77,8 +78,8 @@ fun AppNavigationBar(
|
||||
)
|
||||
} else {
|
||||
val baseColor =
|
||||
if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
if (ThemeConfig.isDeepPersonalizationActive && customSecondaryColor != 0) {
|
||||
Color(customSecondaryColor)
|
||||
} else {
|
||||
GlassDefaults.glassColor(
|
||||
noBlurColor = BottomAppBarDefaults.containerColor,
|
||||
|
||||
+9
-39
@@ -51,31 +51,15 @@ fun GlassMediumFlexibleTopAppBar(
|
||||
val isMiuix = ThemeResolver.isMiuixEngine(composeEngine)
|
||||
|
||||
val containerColor = if (!isMiuix) {
|
||||
if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
GlassTopAppBarDefaults.containerColor()
|
||||
}
|
||||
GlassDefaults.secondaryColorOr { GlassTopAppBarDefaults.containerColor() }
|
||||
} else {
|
||||
if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
GlassTopAppBarDefaults.getMiuixAppBarColor()
|
||||
}
|
||||
GlassDefaults.secondaryColorOr { GlassTopAppBarDefaults.getMiuixAppBarColor() }
|
||||
}
|
||||
|
||||
val scrolledColor = if (!isMiuix) {
|
||||
if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
GlassTopAppBarDefaults.scrolledContainerColor()
|
||||
}
|
||||
GlassDefaults.secondaryColorOr { GlassTopAppBarDefaults.scrolledContainerColor() }
|
||||
} else {
|
||||
if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
GlassTopAppBarDefaults.getMiuixAppBarColor()
|
||||
}
|
||||
GlassDefaults.secondaryColorOr { GlassTopAppBarDefaults.getMiuixAppBarColor() }
|
||||
}
|
||||
|
||||
val animatedColor = if (!isMiuix) {
|
||||
@@ -190,11 +174,7 @@ object GlassTopAppBarDefaults {
|
||||
|
||||
@Composable
|
||||
fun getMiuixAppBarColor(): Color {
|
||||
val baseColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
MiuixTheme.colorScheme.surface
|
||||
}
|
||||
val baseColor = GlassDefaults.secondaryColorOr { MiuixTheme.colorScheme.surface }
|
||||
return GlassDefaults.glassColor(
|
||||
noBlurColor = baseColor,
|
||||
blurAlpha = GlassDefaults.TransparentAlpha
|
||||
@@ -218,9 +198,7 @@ object GlassTopAppBarDefaults {
|
||||
@Composable
|
||||
fun glassColors(): TopAppBarColors {
|
||||
|
||||
val containerBaseColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
val containerBaseColor = GlassDefaults.secondaryColorOr {
|
||||
MaterialTheme.colorScheme.surface
|
||||
}
|
||||
val containerColor = GlassDefaults.glassColor(
|
||||
@@ -228,9 +206,7 @@ object GlassTopAppBarDefaults {
|
||||
blurAlpha = GlassDefaults.TransparentAlpha
|
||||
)
|
||||
|
||||
val scrolledBaseColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
val scrolledBaseColor = GlassDefaults.secondaryColorOr {
|
||||
MaterialTheme.colorScheme.surfaceContainer
|
||||
}
|
||||
val scrolledContainerColor = if (ThemeConfig.enableBlur) {
|
||||
@@ -247,11 +223,7 @@ object GlassTopAppBarDefaults {
|
||||
|
||||
@Composable
|
||||
fun containerColor(): Color {
|
||||
val baseColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
MaterialTheme.colorScheme.surface
|
||||
}
|
||||
val baseColor = GlassDefaults.secondaryColorOr { MaterialTheme.colorScheme.surface }
|
||||
val glassColor = GlassDefaults.glassColor(
|
||||
noBlurColor = baseColor,
|
||||
blurAlpha = GlassDefaults.TransparentAlpha
|
||||
@@ -261,9 +233,7 @@ object GlassTopAppBarDefaults {
|
||||
|
||||
@Composable
|
||||
fun scrolledContainerColor(): Color {
|
||||
val baseColor = if (ThemeConfig.enableDeepPersonalization && ThemeConfig.secondaryThemeColor != 0) {
|
||||
Color(ThemeConfig.secondaryThemeColor)
|
||||
} else {
|
||||
val baseColor = GlassDefaults.secondaryColorOr {
|
||||
MaterialTheme.colorScheme.surfaceContainer
|
||||
}
|
||||
val glassColor = GlassDefaults.glassColor(
|
||||
|
||||
Reference in New Issue
Block a user