1.无参数 对象
class User2 @Inject constructor() {
var age:Int?=null
override fun toString(): String {
return "User2(age=$age)"
}
}
2.搞一个 注入生成类
@Component
public interface MainComponent2 {
fun a(activity: MainActivity)
}
3.在使用Activity 中调用
@Inject
lateinit var user2: User2
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
DaggerMainComponent.builder().build().inject(this)
}
自己的推断。当年你在Activity中标记了Inject 对象时,调用了 dragger inject。那么生成的DragComponent 就会把你标注的对象导入进去。

这时候会检查你的标注了Inject 的对象 与你调用的 drag inject 参数是否匹配。如果不匹配,直接编译不通过。
可以在同一个activity 中执行不同component中相同构造函数的对象的inject注入。不能执行不同component 不同构造函数对象的inject注入。
举个例子
class User2 @Inject constructor() {
var age:Int?=null
override fun toString(): String {
return "User2(age=$age)"
}
}
class User @Inject constructor(var age:Int) {
var name:String?=null
override fun toString(): String {
return "name=$name age=$age"
}
}
@Singleton
@Component(modules = [MainModule::class])
public interface MainComponent {
fun inject(activity: MainActivity)
}
@Singleton
@Component(modules = [MainModule::class])
public interface MainComponent2 {
fun a(activity: MainActivity)
}
@Inject
lateinit var user: User
@Inject
lateinit var dog: Dog
@Inject
lateinit var hahahaha: Hahahaha;
@Inject
lateinit var user2: User2
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
DaggerMainComponent.builder().build().inject(this)
DaggerMainComponent2.builder().build().a(this)
hello_world_tv.setOnClickListener {
user.name="hhh"
dog.user.name="张三"
dog.name="汪汪汪"
Log.d("test","${user==dog.user}")
hello_world_tv.text=dog.toString()
}
}
是可以正常运行的。但是如果把MainComponent2 改下。
@Component
public interface MainComponent2 {
fun a(activity: MainActivity)
}
就运行不了。 当然,如果你去改user2,然后必然也要改MainComponent2 中的provide。也是执行不了的。执行不了的原因就是,在component2中回去尝试构建user,但是发现没有user的provide构造函数。所以执行失败了。每个component 都会去吧所以标注了inject的对象尝试去构建出来。
标注了inject 的Bean 对象,在使用时,调用了 component 的inject 时会把对象的包导入进去,如果 构造参数不符合规则,就会编译不过。所以两个相同的,编译可以执行。如果两个不一样的,会尝试吧所以的都导入到一个component中。自然编译不过
inject 跟通过构造方法生成桥梁的区别是:
例:
@Module
class AppModule(private val context: Context) {
@Provides
fun provideSp(): SharedPreferences {
return context.getSharedPreferences("sp", Context.MODE_PRIVATE)
}
//绑定桥梁
fun testInject(){
DaggerAppComponent.builder()
.appModule(AppModule(this))
.build().inject(this)
}
}
构造方法的方式会通过 在build的时候、
``
public Builder appModule(AppModule appModule) {
this.appModule = Preconditions.checkNotNull(appModule);
return this;
}
public AppComponent build() {
Preconditions.checkBuilderRequirement(appModule, AppModule.class);
return new DaggerAppComponent(appModule);
}
``
把生成的对象传入。
inject 会检查绑定对象是否存在inject对象。对比:


自定义作用域
java:
@Scope //声明这是一个自定义@Scope注解
@Retention(RUNTIME)
public @interface ActivityScope {
}
KT:
@Documented
@Scope
@Retention(AnnotationRetention.RUNTIME)
annotation class Activit
2022年3月26日16:53:58
关于作用域的理解,作用域并不能解决什么问题。对象的绑定主要来源于 component,同一个component中,标记了相同scope 作用域的对象,只会产生同一个,inject方法其实只是对象的引用赋值
@Override
public void inject(BActivity activity) {
injectBActivity(activity);
}
private AActivity injectAActivity(AActivity instance) {
AActivity_MembersInjector.injectPlane1(instance, providerAnPlaneProvider.get());
AActivity_MembersInjector.injectPlane2(instance, providerAnPlaneProvider.get());
return instance;
}
@InjectedFieldSignature("com.example.learndragger.testscope.AActivity.plane1")
public static void injectPlane1(AActivity instance, AirPlane22 plane1) {
instance.plane1 = plane1;
}
观看生成代码,只是把页面的标记了@inject对象的引用 指向了component生成的对象。所以如果不同的页面,使用了同一个component,那么他们引用的就可以是同一个对象。(但是只标记了scope 的对象)。没有任何scope标记的对象,每次都会生成新的对象,标记了scope的对象,会做一个 双重检查,每次返回同一个对象。
component通过build 生成对应的component对象,它可以不用赋值到具体的对象(activity/fragment),可以引用到别的component中,规则是
1。不同的component不能使用相同的作用域scoope 标记
2。没有使用scope的component不能依赖使用了scope的component
网友评论