Почему он все еще работает без установки AndroidInjectionModule?
Согласно документацииDagger о введении объектов активности , в ней говорится, что установка AndroidInjectionModule
в вашем компоненте приложения. Впрочем, все прекрасно и без этого.
Например:
Введенный экземпляр
data class Food(val name: String)
Модуль
@Module
class FoodModule{
@Provides
fun provideFood(): Food {
return Food("cholocate")
}
}
BindingModule
@Module
abstract class MainActivityModule {
@ContributesAndroidInjector(modules = [FoodModule::class])
abstract fun FoodShop(): MainActivity
}
Аппкомпонент (без установки AndroidInjectionModule)
@Component(modules = [MainActivityModule::class])
interface AppComponent{
fun inject(app: App)
}
Приложение
class App : Application(), HasActivityInjector {
@Inject
lateinit var dispatchingActivityInjector: DispatchingAndroidInjector<Activity>
override fun onCreate() {
super.onCreate()
DaggerAppComponent.create().inject(this)
}
override fun activityInjector(): AndroidInjector<Activity> {
return dispatchingActivityInjector
}
}
Основная активность
class MainActivity : AppCompatActivity() {
@Inject
lateinit var food: Food
override fun onCreate(savedInstanceState: Bundle?) {
AndroidInjection.inject(this)
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
Log.d("test", "Get ${food.name}")
}
}
Он получает шоколад успешно в MainActivity.
1 ответ:
Означает ли это, что мне не нужно объявлять об этом? При каких обстоятельствах это будет неправильно?На самом деле кажется, что вам не нужно объявлять его, но это может привести к ошибкам компиляции, если вы этого не сделаете.
Если вы посмотрите на AndroidInjectionModule, вы увидите, что он просто перечисляет кучу методов
@Multibinds
для типов фреймворков.@Multibinds abstract Map<Class<? extends Activity>, AndroidInjector.Factory<? extends Activity>> activityInjectorFactories();
Теперь, если вы посмотрите вверх Объявление
@Multibinds
Вы можете прочитать, чтоВы делаете не нужно использовать
@Multibinds
для наборов или карт, которые имеют хотя бы один@IntoSet
,@ElementsIntoSet
, или@IntoMap
привязка, но вы должны объявить их, если они могут быть пустыми.И объявлять их, если они могут быть пустыми - это именно то, что модуль
AndroidInjectionModule
делает для вас. Если части впрыска Android потребуют неопределенной карты заводов инжекторов, вы, вероятно, получите ошибку времени компиляции, заявив, что она не может быть предоставлена.Причина, по которой вам не нужен модуль, заключается в следующем потому что вы используете
@ContributesAndroidInjector
, из которого сгенерированный код будет содержать метод@Binds @IntoMap etc.
, который объявляет карту Привязок. Как указано выше-поскольку он больше не пустой-вам не понадобится дополнительное объявление@Multibinds
, котороеAndroidInjectionModule
обеспечивает непустую многосвязку.
Вы можете ненуждаться в модуле, но он объявит все фабрики инжекторов фреймворка для вас в случае, если они могут быть пустыми, возможно, предотвращая одну или две ошибки компиляции. После того, как весь javadoc просто утверждает, что это должен устанавливаться, а не то, что он должен.
Этот модуль должен быть установлен в компоненте, который используется для внедрения класса приложения.