martmists
07/01/2024, 12:48 PMval theme by settings.bound<AppTheme>(default=MaterialAppTheme(isSystemInDarkTheme()))
but if I change this value elsewhere in the code, I need to tell this part to reload and trigger a recomposition. How would I do this? I tried reading the source for MutableState but didn't quite understand how that triggered recompositions. Relevant Delegate class in thread.martmists
07/01/2024, 12:49 PM@Suppress("UNCHECKED_CAST")
class BoundSetting<T>(private val settings: Settings, private val key: String?, private val default: T?, private val type: KType, private val serializer: KSerializer<T>) {
operator fun getValue(thisRef: Any?, property: KProperty<*>): T {
@Suppress("IMPLICIT_CAST_TO_ANY")
val res = when (type) {
String::class -> settings.getStringOrNull(key ?: property.name)
Int::class -> settings.getIntOrNull(key ?: property.name)
Long::class -> settings.getLongOrNull(key ?: property.name)
Float::class -> settings.getFloatOrNull(key ?: property.name)
Double::class -> settings.getDoubleOrNull(key ?: property.name)
Boolean::class -> settings.getBooleanOrNull(key ?: property.name)
else -> settings.getStringOrNull(key ?: property.name)?.let { Json.decodeFromString(serializer, it) }
}
return (res ?: default) as T
}
operator fun setValue(thisRef: Any?, property: KProperty<*>, value: T?) {
if (value == null) {
settings.remove(key ?: property.name)
return
}
when (type) {
String::class -> settings.putString(key ?: property.name, value as String)
Int::class -> settings.putInt(key ?: property.name, value as Int)
Long::class -> settings
Float::class -> settings
Double::class -> settings
Boolean::class -> settings
else -> settings.putString(key ?: property.name, Json.encodeToString(serializer, value))
}
}
companion object {
inline operator fun <reified T> invoke(settings: Settings, key: String?, default: T): BoundSetting<T> {
return BoundSetting(settings, key, default, typeOf<T>(), serializer())
}
inline operator fun <reified T> invoke(settings: Settings, key: String?): BoundSetting<T?> {
return BoundSetting(settings, key, null, typeOf<T>(), serializer())
}
}
}
martmists
07/01/2024, 12:50 PMSettings.bound(...)
are just simple functions that call BoundSetting(this, ...)
martmists
07/01/2024, 12:53 PMsetValue
calls just trigger a recomposition for the relevant getValue
calls made elsewhere. Note that I want val x by settings.bound(...)
to be recomposed by a modification from elsewhere; Basically, if getValue would return a different value if called again, it should recompose.martmists
07/01/2024, 12:54 PMSettings.getX
calls, only Settings.put
calls would modify it.Landry Norris
07/01/2024, 6:51 PMmartmists
07/01/2024, 7:33 PM