I have a flow of the events, there are two types of events - initial or non-initial.
data class Event(
isInitial: boolean,
)
val flow: MutableStateFlow<Event?> = MutableStateFlow(null)
Initial event might be produced only once. Non-initial events might be produced many times before or after initial.
In my view model I need to collect the events, but the initial events should be processed first, then non-initial, even if they were emitted earlier.
How to achieve this behaviour? What flow operators would help?
I don't know of any ready to use operators like this, but we can easily write our own, by temporarily storing items in the buffer:
fun <T> Flow<T>.pullSingleToFront(predicate: (T) -> Boolean) = flow {
val buf = mutableListOf<T>()
var found = false
collect { item -> when {
found -> emit(item)
!predicate(item) -> buf += item
else -> {
found = true
emit(item)
buf.forEach { emit(it) }
buf.clear()
}
}}
}
Example:
suspend fun main() {
flow {
emit(Event(2))
emit(Event(3))
emit(Event(1, isInitial = true))
emit(Event(4))
emit(Event(5))
}
.pullSingleToFront { it.isInitial }
.collect { println(it) } // 1, 2, 3, 4, 5
}
data class Event(
val id: Int,
val isInitial: Boolean = false,
)
Still, this kind of requirements doesn't fit flows very well. I agree with @tyg that maybe you need a code redesign of some sort.