这种“DI”的方法有两个问题:
-
就像OP所说的:我们需要在需要注入的地方复制并粘贴这个样板文件,这很乏味,也很难重构。
-
被注射者(例如。
Activity
)应该不知道在哪里
@Inject
实例来自,它关心的只是“嘿,给我一个实例”。
为了解决上述问题,
dagger.android
-
创建
AndroidInjector
对于每个组件。
// App component
@Singleton
@Component(
modules = [
AndroidSupportInjectionModule::class, // build-in module
ActivityBindingModule::class,
AppModule::class
]
)
interface AppComponent : AndroidInjector<MainApplication> {
// we need to bind `MainApplication` instance to this component,
// so we have a builder here.
@Component.Builder
abstract class Builder : AndroidInjector.Builder<MainApplication>()
}
// Each controller (e.g. `Activity` / `Fragment` / `Service`) subcomponents
@Module
abstract class ActivityBindingModule {
// will generate a FooActivitySubcomponent under ActivityBindingModule's component
@ActivityScoped
@ContributesAndroidInjector(modules = [FooModule::class])
internal abstract fun fooActivity(): FooActivity
@ActivityScoped
@ContributesAndroidInjector(modules = [BarModule::class])
internal abstract fun barActivity(): BarActivity
}
-
把你的
s、 所以它可以在步骤1中使用提供的注入器为我们进行注射。
// App component
class MainApplication : DaggerApplication() {
override fun applicationInjector(): AndroidInjector<out DaggerApplication> {
return DaggerAppComponent.builder().create(this)
}
}
// Each controller subcomponents
class FooActivity : DaggerAppCompatActivity() {
@Inject lateinit var foo: Foo
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
// no need to call inject() here anymore!
foo.doSth()
}
}
举个具体的例子:签出
iosched