【发布时间】:2017-12-13 05:17:50
【问题描述】:
我知道通常使用 Kotlin 应该不会有什么不同,但我遇到了一些奇怪的情况,即 @Named 限定符需要 Kotlin 中的范围。
我有一个 ViewHolderFactory 类,它允许我创建视图类型的简单映射 -> 视图持有者类:
@Singleton
class ViewHolderFactoryImpl @Inject constructor(
private val viewHolderComponentProvider: Provider<ViewHolderSubcomponent.Builder>
): ViewHolderFactory(mapOf(
R.layout.view_error to ErrorViewHolder::class.java,
R.layout.view_soft_error to SoftErrorViewHolder::class.java,
R.layout.view_empty to EmptyViewHolder::class.java,
R.layout.view_loading to LoadingViewHolder::class.java,
R.layout.item_got_it to GotItViewHolder::class.java)) {
override fun createViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder {
val viewHolder = super.createViewHolder(parent, viewType)
if (viewHolder is Injectable) {
viewHolderComponentProvider.get()
.viewHolder(viewHolder)
.build()
.inject(viewHolder)
}
return viewHolder
}
}
ViewHolderSubcomponent 定义如下,目标是能够为每个视图持有者创建一个子组件并注入一些东西:
@ViewHolderScope
@Subcomponent(modules = [ViewHolderModule::class])
interface ViewHolderSubcomponent {
fun inject(viewHolder: RecyclerView.ViewHolder)
fun viewHolder(): RecyclerView.ViewHolder
@Subcomponent.Builder
interface Builder {
@BindsInstance
fun viewHolder(viewHolder: RecyclerView.ViewHolder): Builder
fun build(): ViewHolderSubcomponent
}
}
ViewHolderModule 定义为:
@Module
class ViewHolderModule {
@Provides @ViewHolderScope
fun provideSectionTitleViewHolder(viewHolder: RecyclerView.ViewHolder): SectionTitleViewHolder =
SectionTitleViewHolder(viewHolder.itemView)
}
当我运行应用程序时,我发现注入不起作用,我的@Inject lateinit var 值为空。查看生成的代码,我明白了原因:
@Override
public void inject(RecyclerView.ViewHolder viewHolder) {
MembersInjectors.<RecyclerView.ViewHolder>noOp().injectMembers(viewHolder);
}
没有为此子组件创建MembersInjectors<RecyclerView.ViewHolder>。我不知道如何让它工作。我知道我应该能够注入不是由 dagger 创建的对象,我只是无法弄清楚我在这里缺少什么。
哦,如果有帮助的话,我确实确保将ViewHolderSubcomponent 包含在我的AppModule 的subcomponents 列表中
【问题讨论】:
-
我不是 100% 确定,但如果您的字段看起来像
@Inject lateinit var,它们可能不会在类文件中以@Inject注释字段结束。我仍在尝试将我的大脑包裹在how Kotlin handles annotations 周围,但请尝试@field:Inject以防万一,并且绝对将其用于@Named和this SO answer 的其他限定符注释。另外,请发布 ViewHolder 代码:目前,Dagger 似乎找不到任何@Inject字段,直到我们看到它,我才能做得更好。