1

假设这样的视图模型:

public class FooViewModel extends AndroidViewModel {

    @Inject public FooViewModel(Application app, SavedStateHandle handle, Bar bar) {
        // ...
    }
}

我想Bar使用 Dagger 2 进行注入。我正在 Android 上开发。

根据SavedStateHandle文档

SavedStateViewModelFactory如果你想在ViewModel的构造函数中接收这个对象,你应该使用。

但是,SavedStateViewModelFactory文档指出工厂是final这意味着我也不能Bar在那里注入。

到目前为止,我一直在通过 setter 进行注入:

    @Provides
    FooViewModel provideFooViewModel(ViewModelStoreOwner owner, Bar bar) {
        FooViewModel viewModel = new ViewModelProvider(owner).get(FooViewModel.class);

        viewModel.setBar(bar);

        return viewModel;
    }

有一个更好的方法吗?

我想使用构造函数注入,将Bar实例变量标记为final并消除setter。

4

1 回答 1

1

要提供FooViewModel,您需要自定义实现AbstractSavedStateViewModelFactory

MyComponent component = DaggerMyComponent.withViewModelStoreOwner(this)
.withSavedStateRegistryOwner(this)
.withDefaultArguments(this.arguments != null ? this.arguments : new Bundle())
.build();

    @Provides
    @Suppress("UNCHECKED_CAST")
    public MyViewModel viewModel(ViewModelStoreOwner viewModelStoreOwner, SavedStateRegistryOwner savedStateRegistryOwner, Bundle defaultArgs, Application application, Bar bar) {
        return new ViewModelProvider(
            viewModelStoreOwner,
            new AbstractSavedStateViewModelFactory(savedStateRegistryOwner, defaultArgs) {
                @Override
                public <T extends ViewModel> T create(
                    String key,
                    Class<T> modelClass,
                    SavedStateHandle handle) {
                    return (T) new MyViewModel(application, handle, bar);
                } 
            }).get(MyViewModel.class);
        });
    }

笔记:

1.)您只能进入SavedStateHandleAbstractSavedStateViewModelFactory因此您将无法将其放入图表中。

2.) 您可以使用https://github.com/square/AssistedInject减少该提供程序的长度。理论上 AutoFactory 也可以工作,但相比之下似乎没有维护。

3.) 你将无法使用@Inject你的 ViewModel。

这个答案部分改编自https://github.com/Zhuinden/DaggerViewModelExperiment/blob/c3cbf0a5bc85467cec08755fcc152db5e8c55f91/app/src/main/java/com/zhuinden/daggerviewmodelexperiment/features/second/SecondFragment.kt#L32-L47

于 2020-04-17T20:33:40.197 回答