UiEvents.kt
Each line, with the release that last changed it.
| 0.5.0 | 1 | package dev.stave.ui.events |
| 2 | ||
| 3 | import kotlinx.coroutines.channels.BufferOverflow | |
| 4 | import kotlinx.coroutines.flow.MutableSharedFlow | |
| 5 | import kotlinx.coroutines.flow.SharedFlow | |
| 6 | import kotlinx.coroutines.flow.asSharedFlow | |
| 7 | ||
| 8 | /** | |
| 9 | * App-wide bus for transient user-facing notifications. Emitters post strings; | |
| 10 | * [dev.stave.desktop.ui.ToastHost] in StaveApp collects them into a small stack of | |
| 11 | * Material Snackbar-style banners. | |
| 12 | * | |
| 13 | * **Design.** MutableSharedFlow with replay=0 (a toast that arrives before a | |
| 14 | * collector is ready is dropped — we don't want last week's error flashing up on | |
| 15 | * today's launch) and extraBufferCapacity=4 so a brief burst (e.g. three playlist | |
| 16 | * loads failing in quick succession) queues rather than dropping. | |
| 17 | * | |
| 18 | * **What goes here.** Non-blocking informational messages that the user can safely | |
| 19 | * ignore. Examples: "Lyrics unavailable for this track", "Couldn't reach LRCLIB", | |
| 20 | * "Playlist saved to library", "Tag reader timed out". **Not** here: fatal errors | |
| 21 | * that should prevent a user action from completing (those deserve a dialog), or | |
| 22 | * status that's not time-bounded (those belong in the relevant screen's persistent | |
| 23 | * UI). | |
| 24 | */ | |
| 25 | class UiEvents { | |
| 26 | private val _messages = MutableSharedFlow<String>( | |
| 27 | replay = 0, | |
| 28 | extraBufferCapacity = 4, | |
| 29 | onBufferOverflow = BufferOverflow.DROP_OLDEST, | |
| 30 | ) | |
| 31 | ||
| 32 | /** Observe toast messages. Collectors are fire-and-forget; missed emissions | |
| 33 | * while no collector is attached stay missed, which is what we want. */ | |
| 34 | val messages: SharedFlow<String> = _messages.asSharedFlow() | |
| 35 | ||
| 36 | /** Post a toast. Non-suspending for convenience in non-coroutine call sites | |
| 37 | * (IO error handlers, VLCJ callbacks). Drops on overflow — at which point the | |
| 38 | * user probably has bigger problems than one dropped toast. */ | |
| 39 | fun post(message: String) { | |
| 40 | _messages.tryEmit(message) | |
| 41 | } | |
| 42 | } |


