Shakil Karim
01/04/2023, 10:47 AMShakil Karim
01/04/2023, 10:47 AM@Composable
public inline fun <reified T : ViewModel> hiltViewModel(viewModelProviderFactory: ViewModelProvider.Factory? = null) : T {
val context = LocalContext.current
val viewModelStoreOwner = LocalViewModelStoreOwner.current
val owner = LocalSavedStateRegistryOwner.current
return remember(key1 = T::class) {
val activity = context.componentActivity
val factory = NavigatorHiltViewModelFactories.getFactory(
activity = activity,
owner = owner,
delegateFactory = viewModelProviderFactory
)
val provider = ViewModelProvider(viewModelStoreOwner ?: activity, factory)
provider[T::class.java]
}
}
public object NavigatorHiltViewModelFactories {
public fun getFactory(
activity: ComponentActivity,
owner: SavedStateRegistryOwner,
delegateFactory: ViewModelProvider.Factory?
): ViewModelProvider.Factory {
return EntryPoints.get(activity, ViewModelFactoryEntryPoint::class.java)
.internalViewModelFactory()
.fromActivity(activity, owner, delegateFactory)
}
internal class InternalViewModelFactory @Inject internal constructor(
private val application: Application,
@HiltViewModelMap.KeySet private val keySet: Set<String>,
private val viewModelComponentBuilder: ViewModelComponentBuilder
) {
fun fromActivity(
activity: ComponentActivity,
owner: SavedStateRegistryOwner,
delegateFactory: ViewModelProvider.Factory?
): ViewModelProvider.Factory {
val defaultArgs = activity.intent?.extras
val delegate = delegateFactory ?: SavedStateViewModelFactory(application, owner, defaultArgs)
return HiltViewModelFactory(owner, defaultArgs, keySet, delegate, viewModelComponentBuilder)
}
}
@EntryPoint
@InstallIn(ActivityComponent::class)
internal interface ViewModelFactoryEntryPoint {
fun internalViewModelFactory(): InternalViewModelFactory
}
}
Shakil Karim
01/04/2023, 10:51 AMval backStack = rememberSaveableBackStack {
push(SaveableBackStack.Record("Home"))
}
Navigator(backStack) {
route("Home") {
val hiltViewModel = hiltViewModel<PackDetailViewModel>()
Box(modifier = Modifier.fillMaxSize()) {
Button(onClick = { backStack.push(SaveableBackStack.Record("Details")) }) {
//Text("${hiltViewModel.uiState}")
}
}
}
route("Details") {
val hiltViewModel = hiltViewModel<CategoryDetailViewModel>()
Box(modifier = Modifier.fillMaxSize()) {
Text("${hiltViewModel.uiState}")
}
}
}