我在 ViewModel 类中有几个 StateFlow 字段。它是添加/编辑表单屏幕,其中每个 StateFlow 都是屏幕上每个可编辑字段的验证属性。
我想写一些带有 StateFlow 属性的 FormValidation 类来验证整个表单的状态。该字段的值基于所有字段的验证状态值,当所有字段有效时发出 true,当任何字段无效时发出 false。
像这样的东西:
class FormValidation(initValue: Boolean, vararg fieldIsValid: StateFlow<Boolean>) {
private val _isValid = MutableStateFlow(initValue)
val isValid: StateFlow<Boolean> = _isValid
init {
// todo: how to combine, subscribe and sync values of all fieldIsValid flows?
}
}
我知道如何做到这一点,LiveData<Boolean>
但MediatorLiveData
我不明白如何做到这一点。
基于@tenfour04 答案的解决方案
class BooleanFlowMediator(scope: CoroutineScope, initValue: Boolean, vararg flows: Flow<Boolean>) {
val sync: StateFlow<Boolean> = combine(*flows) { values ->
values.all { it }
}.stateIn(scope, SharingStarted.Eagerly, initValue)
}
带有 StateFlow 和 ViewModel 的演示代码
class SyncViewModel : ViewModel() {
companion object {
private const val DEFAULT_VALUE: Boolean = false
}
private val values: List<List<Boolean>> = listOf(
listOf(false, false, false),
listOf(true, false, false),
listOf(false, true, true),
listOf(true, true, true)
)
private var index: Int = 0
private val _flow1 = MutableStateFlow(DEFAULT_VALUE)
val flow1: StateFlow<Boolean> = _flow1
private val _flow2 = MutableStateFlow(DEFAULT_VALUE)
val flow2: StateFlow<Boolean> = _flow2
private val _flow3 = MutableStateFlow(DEFAULT_VALUE)
val flow3: StateFlow<Boolean> = _flow3
val mediator = BooleanFlowMediator(viewModelScope, DEFAULT_VALUE,
flow1, flow2, flow3)
fun generateValues() {
val idx = (index + 1).mod(values.size).also { index = it }
val row = values[idx]
_flow1.value = row[0]
_flow2.value = row[1]
_flow3.value = row[2]
}
}