前言:清楚dagger定义的层次也就实现了组件化。例如需要注入Application、Activity、LifecycleProvider参数,这些参数在基础库lib_base里定义,而由于inject()需要注入到具体的activity或fragment中,因此需要在上层业务库lib_use中定义。
实现:
一、注入Application
1、定义数据源
@Module
class AppModule(private val context: Application) {
@Provides
@Singleton
fun providesContext(): Context {
return context
}
}
2、定义数据组织者
@Singleton
@Component(modules = arrayOf(AppModule::class))
interface AppComponent {
fun context(): Context
}
3、在lib_base中的BaseApplication中生成Application数据组织者
open class BaseApplication : MultiDexApplication() {
lateinit var appComponent: AppComponent
override fun onCreate() {
appComponent = DaggerAppComponent.builder()
.appModule(AppModule(this))
.build()
}
}
二、注入Activity、LifecycleProvider
1、定义Activity数据源
@Module
class ActivityModule(private val activity: Activity) {
@ActivityScope
@Provides
fun providesActivity(): Activity {
return activity
}
}
2、定义LifecycleProvider数据源
@Module
class LifecycleProviderModule(private val lifecycleProvider: LifecycleProvider<*>) {
@Provides
fun provideLifecycleProvider(): LifecycleProvider<*> {
return this.lifecycleProvider
}
}
3、定义Activity和LifecycleProvider组织者
@ActivityScope
@Component(dependencies = arrayOf(AppComponent::class), modules = arrayOf(ActivityModule::class, LifecycleProviderModule::class))
interface ActivityComponent {
fun context(): Context
fun activity(): Activity
fun lifecycleProvider(): LifecycleProvider<*>
}
4、定义区间注解(下面详解)
@Scope
@Retention(AnnotationRetention.RUNTIME)
annotation class PerComponentScope
@Scope
@Retention(AnnotationRetention.RUNTIME)
annotation class ActivityScope
5、在lib_base中的Activity基类中生成Activity、LifecycleProvider数据组织者
abstract class BaseMvpActivity<T : BasePresenter<*>> : BaseActivity(), BaseView {
@Inject
lateinit var mPresenter: T
lateinit var mActivityComponent: ActivityComponent
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
initInjection()
}
private fun initInjection() {
mActivityComponent = DaggerActivityComponent.builder()
.appComponent((application as BaseApplication).appComponent)
.activityModule(ActivityModule(this))
.lifecycleProviderModule(LifecycleProviderModule(this))
.build()
injectComponent()
}
protected abstract fun injectComponent()
}
三、在业务层注入依赖
1、定义数据组织者
@PerComponentScope
@Component(dependencies = arrayOf(ActivityComponent::class))
interface UserComponent {
fun inject(activity: LoginActivity)
}
2、生成数据组织者并注入依赖
class LoginActivity : BaseMvpActivity<LoginPresenter>(), LoginView{
override fun injectComponent() {
DaggerUserComponent.builder()
.activityComponent(mActivityComponent)
.build()
.inject(this)
mPresenter.mView = this
}
}
四、讲解一下@Scope自定义区间
1、区间是与组织者Component相关联的,意义是针对同一个组织者注入的数据源为单例。例如需要注入Test对象,数据源是通过new提供的而非上文构造传参方式,在LoginActivity中注入testOne: Test和testTwo: Test则testOne和testTwo为两个对象,而使用自定义区间后则testOne和testTwo为同一对象。如在RegistActivity中注入test:Test则和LoginActivity中注入的非同一个对象,毕竟UserComponent非同一对象。
2、@Singleton为Dagger预定义的Scope
3、自定义区间名称可以任意,区间本身并不能定义单例区间大小,是由Component对象决定的,@Singl同理。
4、全局单例则将Component全局唯一,如在application中生成的AppComponent对象则保证了提供的数据源全局唯一
五、总结
在业务层定义新activity时,需在业务层Component中添加inject(activity: 自定义activity),然后重写该activity的injectComponent方法可以直接拷贝步骤三的2中代码,注意由于inject()必须指定注入到具体Activity类,所以无法将injectComponent方法在基类activity中进行实现,以至于每新建activity需要进行上面两步操作。