We all know ViewModel is build to hold ui state and survive configuration change, so by this given it should retrieve the data needed to create ui state as soon as possible, most of the time that mean when you initialize it, what if you need to pass an id to that ViewModel like postId or articleId, when you use hilt the dependencies of the Viewmodel must be known at compile time if you want Hilt to inject them without any effort, what happen if you want to pass runtime dependencies,
the solution:
first: create @AssistedFactory Annotated Interface
@AssistedFactory
interface UserViewModelAssistedFactory {
fun create(name: String): UserViewModel
}
second: create factory class or object
class Factory(
private val assistedFactory: UserViewModelAssistedFactory,
private val name: String,
) : ViewModelProvider.Factory {
override fun <T : ViewModel?> create(modelClass: Class<T>): T {
return assistedFactory.create(name) as T
}
}
third: inject the factory in fragment and use it to create the viewModle
@Inject
lateinit var assistedFactory: UserViewModelAssistedFactory
private val userViewModel: UserViewModel by viewModels {
UserViewModel.Factory(assistedFactory, navArgs.name)
}
this is so much right I felt the same.
it turns out that if your dependices is coming from Navigation argument you can use the provided by defualt SavedStateHandle to get that navArgs, it comes with this version,
implementation 'androidx.navigation:navigation-ui-ktx:2.4.1'
you can access navigation arguments through the saved state handle
@HiltViewModel
class RecentChatViewModel @Inject constructor(
private val getRecentChatUseCase: GetRecentChatUseCase,
savedStateHandle: SavedStateHandle
) : ViewModel() {
private val accountId: Int = RecentChatFragmentArgs.
fromSavedStateHandle(savedStateHandle).accountId
be careful you will need to update your compile sdk to 31 if
you are not.
it is simple right why I had to search so much me and my friend Elfiky to reach out this simple solution.
I copied some code from this article because I am lazy
Top comments (0)