KViewModel

open class KViewModel<State>(initialState: State, application: Application) : AndroidViewModel, KoinComponent(source)

Legacy base ViewModel for Kindling applications that require AndroidViewModel or KoinComponent integration.

KViewModel is the original single-type-parameter tier of the Kindling ViewModel hierarchy. It provides state management, one-shot events, and async helpers while remaining compatible with Koin's by inject() delegation and the Application context.

This ViewModel follows a simplified MVI (Model-View-Intent) pattern where:

  • State is a single observable object (usually a data class).

  • Events are one-shot side effects (navigation, toasts, etc.).

When to use which ViewModel

ScenarioRecommended base
Needs Application context or Koin by inject()KViewModel ← you are here
Simple screen, no framework coupling neededdev.kindling.compose.legacy.KSimpleViewModel
Feature screen with a typed event contractKViewModel (two-param)
Strict unidirectional MVI flowKMviViewModel

Basic usage

data class ProfileState(
val isLoading: Boolean = true,
val user: User? = null
)

sealed interface ProfileEvent {
data class ShowToast(val message: String) : ProfileEvent
}

class ProfileViewModel(
application: Application,
private val repository: UserRepository
) : KViewModel<ProfileState>(
initialState = ProfileState(),
application = application
) {
// Koin injection supported
private val analytics: AnalyticsService by inject()

init {
loadProfile()
}

private fun loadProfile() {
fetchData(
source = { repository.getUser() },
onResult = { result ->
result
.onSuccess { user ->
updateState { copy(user = user, isLoading = false) }
analytics.logEvent("profile_loaded")
}
.onFailure {
updateState { copy(isLoading = false) }
sendEvent(ProfileEvent.ShowToast("Failed to load profile"))
}
}
)
}

fun onLogoutClick() {
sendEvent(AppScreen.Login) // Automatic navigation if AppScreen implements KDestination
}
}

Parameters

initialState

The state emitted immediately to all collectors on subscription.

application

The Application instance, forwarded to AndroidViewModel.

Type Parameters

State

The UI state type. Prefer immutable data classes with default values.

See also

Constructors

Link copied to clipboard
constructor(initialState: State, application: Application)

Properties

Link copied to clipboard
val events: Flow<Any>

One-shot UI event stream.

Link copied to clipboard
val state: StateFlow<State>

Observable UI state stream.

Functions

Link copied to clipboard
open fun addCloseable(closeable: AutoCloseable)
fun addCloseable(key: String, closeable: AutoCloseable)
Link copied to clipboard
fun <T> collectData(source: suspend () -> Flow<T>, onResult: Result<T>.() -> Unit)

Collects a Flow returned by source on Dispatchers.IO and delivers each Result to onResult on Dispatchers.Main.

Link copied to clipboard
fun <T> fetchData(source: suspend () -> T, onResult: Result<T>.() -> Unit)

Executes a suspending source on Dispatchers.IO and delivers the Result to onResult on Dispatchers.Main.

Link copied to clipboard
open fun <T : Application> getApplication(): T
Link copied to clipboard
Link copied to clipboard
open fun getKoin(): Koin
Link copied to clipboard
protected open fun onCleared()
Link copied to clipboard
protected fun sendEvent(obj: Any)

Enqueues a one-time event for the UI layer to consume.

Link copied to clipboard
protected fun updateState(block: State.() -> State)

Applies a reducer function to the current state and emits the result atomically.