介绍
Dagger2是一个依赖注入框架,我们经常用到的依赖注入框架还有ButterKnife。说到这里,首先了解一个概念:控制反转。
控制反转(又叫IOC:Inversion Of Control):是面向对象编程中的一种设计原则,可以用来减低计算机代码之间的耦合度。其中最常见的方式叫做依赖注入(Dependency Injection),还有一种方式叫“依赖查找”(Dependency Lookup)。通过控制反转,对象在被创建的时候,由一个调控系统的所有对象的外界实体将其所依赖的对象的引用传递给它。也可以说,依赖被注入到对象中。
说到Dagger2的使用,我们首先了解的是使用Dagger2有什么好处?
Dagger2是用来使代码解耦的,一个类的new代码是非常可能充斥在app的多个类中的,假如该类的构造函数发生变化,那这些涉及到的类都得进行修改。
如果使用Dagger2的Inject注解构造函数,即使构造函数发生较大的变化,我们基本上都不需要修改任何代码。
基本使用
Dagger2,分为三部分:依赖提供方、依赖需求方、依赖注入容器(即二者之间的桥梁)。
在Dagger2中被@Module注解的类作为提供方、@Component注解的类作为桥梁、@Inject注解的变量作为需求方.
这里说一下@Inject
@Inject注解有两个作用:
作为依赖提供方,@Inject注解添加到类的构造函数上
作为依赖需求方,@Inject注解添加到成员变量上
简介:如果在类上添加此依赖注入,Dagger 就会构造一个这个类的实例并满足他们的依赖。通过这个inject注解可以将依赖需求方对象送到Component类中,Component类就会根据依赖需求方对象中声明的依赖关系来注入依赖需求方对象中所需要的对象
注意:
inject方法的参数不能用父类来接收,
@Inject注解的字段不能是private和protected的。
下面我们就简单说一说,Dagger2的使用步骤:
引入
//Dagger2 依赖注入框架
api 'com.google.dagger:dagger:2.17'
annotationProcessor 'com.google.dagger:dagger-compiler:2.17'
无参使用
1,创建一个类Person,并且在Person类的构造方法上添加上@Inject注解,作为依赖的提供方
import javax.inject.Inject;
public class Student {
@Inject
public Student() {
}
public String show(){
return "我是秀儿";
}
}
2,我们创建ActivityComponent类,将@Inject 的对象自动装入其中,然后提供给activity使用.
@Component
public interface ActivityComponent {
//方法可以有多个. 想在哪个页面中使用就注入到哪个页面
void inject(Main2Activity main2Activity);
void inject(MainActivity mainActivity);
}
3, 在activity中,进行注入使用
public class Main2Activity extends AppCompatActivity {
@Inject
Student student;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main2);
//dagger会在Component前面加入,就是命名了
DaggerActivityComponent.builder().build().inject(this);
String show = student.show();
Toast.makeText(this, show, Toast.LENGTH_SHORT).show();
}
有参使用
1,实体类
public class Student {
private String name;
// @Inject
// public Student() {
// }
@Inject
public Student(String name) {
this.name = name;
}
public String show(){
return "我是秀儿";
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
2,moudel类
@Module
public class StudentModel {
String name;
public StudentModel(String name) {
this.name = name;
}
@Provides
public String getName() {
return name;
}
}
3, component类
@Component(modules = StudentModel.class)
public interface ActivityComponent {
//方法可以有多个. 想在哪个页面中使用就注入到哪个页面
void inject(Main2Activity main2Activity);
void inject(MainActivity mainActivity);
}
4,Activity中使用
public class Main2Activity extends AppCompatActivity {
private static final String TAG = "Main2Activity";
@Inject
Student student;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main2);
//dagger会在Component前面加入,就是命名了
// DaggerActivityComponent.builder().build().inject(this);
DaggerActivityComponent.builder().studentModel(new StudentModel("小明")).build().inject(this);
String show = student.show();
String name = student.getName();
// Toast.makeText(this, show, Toast.LENGTH_SHORT).show();
Log.i(TAG, "onCreate: "+show);
Log.i(TAG, "onCreate: "+name);
}
}
dagger 和mvp结合使用
1,在baseActivity和baseFragment上加上@Inject注解
public abstract class BaseActivity<P extends IPresenter> extends AppCompatActivity implements IActivity,IView {
@Inject
protected P ipresent;
}
public abstract class BaseFragment<P extends IPresenter> extends Fragment implements IFragment,IView {
@Inject
protected P ipresenter;
}
2, 在basePresenter上加
public class BasePresenter<M extends IModel,V extends IView> implements IPresenter {
protected V view;
protected M model;
@Inject
public BasePresenter(V view, M model) {
this.view = view;
this.model = model;
}
@Override
public void destory() {
if(model != null){
model.destory();
model = null;
}
}
}
3, 创建module(因为有参)
@Module
public class FoodModule {
private FoodContract.IFoodView iFoodView;
public FoodModule(FoodContract.IFoodView iFoodView) {
this.iFoodView = iFoodView;
}
@Provides
public FoodContract.IFoodView getiFoodView(){
return iFoodView;
}
@Provides
public FoodContract.IFoodModel getFoodModel(){
return new FoodModel();
}
}
4, 创建桥梁
@Component(modules = FoodModule.class)
public interface MainActivityComponent {
void inject(MainActivity mainActivity);
}
5, 使用
@Override
public void initDate() {
// ipresent = new FoodPresenter(this, new FoodModel());
DaggerMainActivityComponent.builder().foodModule(new FoodModule(this)).build().inject(this);
ipresent.getFood();
// ipresent.getFood();
}```