There is a hacky way to clear a specific ViewModel instance in which you should create your ViewModel instance with a customized key as stated below, and in order to clear it you should just create another instance (with different ViewModel class such as an EmptyViewModel class) but with the same key.
ShopFragment class:
class shopFragment : BaseFragment() {
fun getViewModel() : ShopViewModel {
return ViewModelProviders.of(activity!!).get(ShopViewModel.KEY, ShopViewModel::class.java)
}
fun clearViewModel() {
ViewModelProviders.of(activity!!).get(ShopViewModel.KEY, EmptyViewModel::class.java)
}
// Fragment logic ...
}
ShopViewModel class:
class ShopViewModel(application: Application) : AndroidViewModel(application) {
companion object {
const val KEY = "ShopViewModel"
}
// view model logic ...
}
EmptyViewModel which is a dummy ViewModel class:
class EmptyViewModel() : ViewModel() {
// A dummy view model!
}
And the magic is happening inside ViewModelProvider class of androidx.lifecycle dependecy, the trick here is revealed when you take a look at the get() function of ViewModelProvider class which retrieves your previous ViewModel instance and compares it with the EmptyViewModel class and as they are not the same, it run mViewModelStore.put(key, viewModel);:
public class ViewModelProvider {
//...
public <T extends ViewModel> T get(@NonNull String key, @NonNull Class<T> modelClass) {
ViewModel viewModel = mViewModelStore.get(key);
if (modelClass.isInstance(viewModel)) {
//noinspection unchecked
return (T) viewModel;
} else {
//noinspection StatementWithEmptyBody
if (viewModel != null) {
// TODO: log a warning.
}
}
viewModel = mFactory.create(modelClass);
mViewModelStore.put(key, viewModel);
//noinspection unchecked
return (T) viewModel;
}
// ...
}
As stated below inside ViewModelStore class of the androidx.lifecycle dependency, the put() method will retrieve the ShopViewModel and clear it, and replace EmptyViewModel instance.
public class ViewModelStore {
//...
final void put(String key, ViewModel viewModel) {
ViewModel oldViewModel = mMap.put(key, viewModel);
if (oldViewModel != null) {
oldViewModel.onCleared();
}
}
//...
}