feat: add infra to create colors mapping

or maybe come up with better idea?
This commit is contained in:
FunkyMuse 2023-06-28 15:46:24 +02:00
parent 90febae626
commit 7f146994ce
3 changed files with 150 additions and 24 deletions

View file

@ -7,7 +7,6 @@ import android.os.Bundle
import android.view.View
import androidx.activity.compose.setContent
import androidx.appcompat.app.AppCompatActivity
import androidx.compose.ui.graphics.Color
import com.simplemobiletools.calculator.compose.screens.SettingsScreen
import com.simplemobiletools.calculator.compose.theme.AppThemeSurface
import com.simplemobiletools.calculator.compose.theme.Theme
@ -30,7 +29,9 @@ class SettingsActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
AppThemeSurface {
AppThemeSurface(
theme = Theme.systemDefaultMaterialYou()
) {
SettingsScreen(
customizeColors = ::handleCustomizeColorsClick, goBack = ::finish,
backgroundColor = getProperBackgroundColor(),

View file

@ -0,0 +1,10 @@
package com.simplemobiletools.calculator.compose.extensions
import android.app.Activity
import android.content.Context
import android.content.ContextWrapper
fun Context.getActivity(): Activity {
if (this is Activity) return this
return if (this is ContextWrapper) baseContext.getActivity() else getActivity()
}

View file

@ -1,21 +1,24 @@
package com.simplemobiletools.calculator.compose.theme
import android.os.Build
import androidx.compose.foundation.LocalOverscrollConfiguration
import androidx.compose.foundation.background
import androidx.compose.foundation.isSystemInDarkTheme
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Surface
import androidx.compose.material3.darkColorScheme
import androidx.compose.material3.lightColorScheme
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.runtime.ReadOnlyComposable
import androidx.compose.material3.*
import androidx.compose.runtime.*
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.luminance
import androidx.compose.ui.graphics.toArgb
import androidx.compose.ui.platform.LocalContext
import com.google.accompanist.systemuicontroller.rememberSystemUiController
import com.simplemobiletools.commons.extensions.*
import com.simplemobiletools.calculator.compose.theme.Theme.Companion.systemDefaultMaterialYou
import com.simplemobiletools.calculator.extensions.config
import com.simplemobiletools.commons.extensions.adjustAlpha
import com.simplemobiletools.commons.extensions.getProperStatusBarColor
import com.simplemobiletools.commons.extensions.isUsingGestureNavigation
import com.simplemobiletools.commons.extensions.navigationBarHeight
import com.simplemobiletools.commons.helpers.HIGHER_ALPHA
@ -57,16 +60,121 @@ fun preferenceSummaryColor(isEnabled: Boolean) =
@Composable
fun preferenceTitleColor(isEnabled: Boolean) = if (isEnabled) Color.Unspecified else disabledTextColor
@Composable
fun getTheme(): Theme {
val context = LocalContext.current
val config = remember { context.config }
//todo ask for help to create all of these mappings for the theme
return systemDefaultMaterialYou()
}
interface CommonTheme {
val primaryColorInt: Int
val backgroundColorInt: Int
val appIconColorInt: Int
val textColorInt: Int
val primaryColor get() = Color(primaryColorInt)
val backgroundColor get() = Color(backgroundColorInt)
val appIconColor get() = Color(appIconColorInt)
val textColor get() = Color(textColorInt)
}
@Stable
sealed class Theme : CommonTheme {
data class SystemDefaultMaterialYou(
override val primaryColorInt: Int,
override val backgroundColorInt: Int,
override val appIconColorInt: Int,
override val textColorInt: Int
) : Theme()
data class AutoLightDark(
override val primaryColorInt: Int,
override val backgroundColorInt: Int,
override val appIconColorInt: Int,
override val textColorInt: Int
) :
Theme()
data class Light(
override val primaryColorInt: Int,
override val backgroundColorInt: Int,
override val appIconColorInt: Int,
override val textColorInt: Int
) : Theme()
data class Dark(
override val primaryColorInt: Int,
override val backgroundColorInt: Int,
override val appIconColorInt: Int,
override val textColorInt: Int
) : Theme()
data class DarkRed(
override val primaryColorInt: Int,
override val backgroundColorInt: Int,
override val appIconColorInt: Int,
override val textColorInt: Int
) : Theme()
data class White(
val accentColor: Int,
override val primaryColorInt: Int,
override val backgroundColorInt: Int,
override val appIconColorInt: Int,
override val textColorInt: Int
) : Theme()
data class BlackAndWhite(
val accentColor: Int,
override val primaryColorInt: Int,
override val backgroundColorInt: Int,
override val appIconColorInt: Int,
override val textColorInt: Int
) : Theme()
data class Custom(
override val primaryColorInt: Int,
override val backgroundColorInt: Int,
override val appIconColorInt: Int,
override val textColorInt: Int
) : Theme()
companion object {
@Composable
fun systemDefaultMaterialYou() = SystemDefaultMaterialYou(
appIconColorInt = LocalContext.current.config.appIconColor,
primaryColorInt = MaterialTheme.colorScheme.primary.toArgb(),
backgroundColorInt = MaterialTheme.colorScheme.background.toArgb(),
textColorInt = (if (isSystemInDarkTheme() || MaterialTheme.colorScheme.background.luminance() < 0.5) Color.White else Color.Black).toArgb()
)
}
}
@Composable
fun Theme(
useTransparentNavigation: Boolean = true,
properBackgroundColor: Int,
content: @Composable () -> Unit,
statusBarColor: Int,
theme: Theme,
content: @Composable () -> Unit,
) {
//todo
val context = LocalContext.current
val systemUiController = rememberSystemUiController()
val colorScheme = when {
theme is Theme.SystemDefaultMaterialYou && Build.VERSION.SDK_INT >= Build.VERSION_CODES.S -> {
if (isSystemInDarkTheme()) dynamicDarkColorScheme(context) else dynamicLightColorScheme(context)
}
theme is Theme.AutoLightDark -> if (isSystemInDarkTheme()) DarkColorScheme else LightColorScheme
theme is Theme.Dark || theme is Theme.DarkRed -> darkColorScheme(primary = theme.primaryColor, background = theme.backgroundColor)
theme is Theme.Light -> lightColorScheme(primary = theme.primaryColor, background = theme.backgroundColor)
theme is Theme.White -> lightColorScheme(primary = theme.primaryColor, background = theme.backgroundColor, tertiary = Color(theme.accentColor))
theme is Theme.BlackAndWhite -> darkColorScheme(primary = theme.primaryColor, background = theme.backgroundColor, tertiary = Color(theme.accentColor))
theme is Theme.Custom -> darkColorScheme(primary = theme.primaryColor, background = theme.backgroundColor)
else -> LightColorScheme
}
LaunchedEffect(Unit) {
if (context.navigationBarHeight > 0 || context.isUsingGestureNavigation() && useTransparentNavigation) {
systemUiController.isNavigationBarVisible = false
@ -74,30 +182,37 @@ fun Theme(
systemUiController.setStatusBarColor(
color = Color(statusBarColor)
)
systemUiController.setNavigationBarColor(Color(properBackgroundColor.adjustAlpha(HIGHER_ALPHA)))
systemUiController.setNavigationBarColor(Color(theme.backgroundColorInt.adjustAlpha(HIGHER_ALPHA)))
}
MaterialTheme(
colorScheme = DarkColorScheme,
content = content,
)
CompositionLocalProvider(
LocalContentColor provides theme.textColor,
LocalOverscrollConfiguration provides null,
) {
MaterialTheme(
colorScheme = colorScheme,
content = content,
)
}
}
@Composable
fun AppThemeSurface(
modifier: Modifier = Modifier,
properBackgroundColor: Int = LocalContext.current.getProperBackgroundColor(),
backgroundColor: Int = MaterialTheme.colorScheme.background.toArgb(),
statusBarColor: Int = LocalContext.current.getProperStatusBarColor(),
theme: Theme = systemDefaultMaterialYou(),
content: @Composable () -> Unit,
) {
Theme(properBackgroundColor = properBackgroundColor, content = {
val context = LocalContext.current
val statusBarColor = remember { context.getProperStatusBarColor() }
Theme(statusBarColor = statusBarColor, theme = theme) {
Surface(
modifier = modifier
.fillMaxSize()
.background(Color(backgroundColor))
.background(theme.backgroundColor)
) {
content()
}
}, statusBarColor = statusBarColor)
}
}