Inject viewModel with hilt

800 views Asked by At

I want to inject my viewModel inside RecyclerView with Hilt. It can be inject but viewModel not destroy when recyclerView destroyed. what is the best way to inject viewModel inside recyclerView with hilt?

2

There are 2 answers

0
Milan Jayan On BEST ANSWER

The best way to do this is to create separate adapter and viewholder classes and then you can inject your viewModel inside that viewholder class instead of the adapter. To destroy the viewModel you should manually do it by observing the parentlifecycle. when the parent lifecycle event is ON_DESTROY do something similar to this in the init block of the adapter class.

parentLifecycle.addObserver(object : LifecycleObserver {

            @OnLifecycleEvent(Lifecycle.Event.ON_DESTROY)
            fun onParentDestroy() {
                recyclerView?.run {
                    for (i in 0 until childCount) {
                        getChildAt(i)?.let {
                            (getChildViewHolder(it) as BaseItemViewHolder<*, *>)
                                .run {
                                    onDestroy()
                                    viewModel.onManualCleared()
                                }
                        }
                    }
                }
            }
  }

Here onManualCleared() function calls onCleared().

0
Amjad Alwareh On

A view model shouldn't be injected inside an adapter, as I read in the comments you can you a better way than that,
Let's imagine you have an adapter with many rows, each row when the user clicks on it, it performs a network call.
First, create an interface

interface Click {
fun onClick(index: Int, item: Model)
}

inside your adapter, init an instance of it then use it in your onBindViewHolder

yourview.setOnClickListener {v-> interface.onClick()}

don't forget to init the interface whether the place you're using it (Activity/Fragment/...).
This is a better solution than using a ViewModel for every row, which may lead to a SystemLeaks.