Dagger2是一个基于JSR-330标准的依赖注入框架,在编译期间自动生成代码,负责依赖对象的创建。为了进一步解耦和方便测试,我们会使用依赖注入的方式构建对象。
使用:
compile 'com.google.dagger:dagger:2.4' annotationProcessor 'com.google.dagger:dagger-compiler:2.4'
一、@Inject 和@component
看图:
public class TestInject { @Inject public TestInject(){} public String getStr(){ return "Test Inject and Component"; } }
@Component public interface TestActivityComponent { void inject(TestActivity testActivity); }
public class TestActivity extends AppCompatActivity { @Inject TestInject testInject; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); DaggerTestActivityComponent.create().inject(this); ((TextView)findViewById(R.id.tv)).setText(testInject.getStr()); } }
二、@module 和 @prodives
无法在第三方库的构造器上加上@Inject注解,可以通过这两个注解
public interface ITest { String getStr(); }
public class Test1 implements ITest { @Override public String getStr() { return "test1"; } }
@Module public class TestModule { @Provides ITest getProvide(){ return new Test1(); } }
@Component(modules = TestModule.class) public interface TestActivityComponent { void inject(TestActivity testActivity); }
public class TestActivity extends AppCompatActivity { @Inject ITest testInject; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); DaggerTestActivityComponent.create().inject(this); ((TextView)findViewById(R.id.tv)).setText(testInject.getStr()); } }
三、@Name
继承同一父类时,通过该标签指定需要实例化的子类
public interface Test { String getStr(); }
public class Test1 implements Test { @Override public String getStr() { return "test1"; } }
public class Test2 implements Test { @Override public String getStr() { return "test2"; } }
@Module public class TestModule { @Provides @Named("Test1") Test1 provideTest1(){ return new Test1(); } @Provides @Named("Test2") Test2 provideTest2(){ return new Test2(); } }
@Component(modules = TestModule.class) public interface TestActivityComponent { void inject(TestActivity testActivity); }
public class TestActivity extends AppCompatActivity { Test1 testInject1; Test2 testInject2; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); DaggerTestActivityComponent.create().inject(this); ((TextView)findViewById(R.id.tv)).setText(testInject2.getStr()); } @Inject public void getTestInject1(@Named("Test1") Test1 test1) { testInject1=test1; } @Inject public void getTestInject2(@Named("Test2") Test2 test2) { testInject2=test2; } }
四、@qualifier
和@Name作用相同,用法不同而已
@Qualifier @Retention(RetentionPolicy.RUNTIME) public @interface Test1 { }
@Qualifier @Retention(RetentionPolicy.RUNTIME) public @interface Test2 { }
public interface Test { String getStr(); }
public class Test1 implements Test { @Override public String getStr() { return "test1"; } }
public class Test2 implements Test { @Override public String getStr() { return "test2"; } }
@Module public class TestModule { @Provides @com.example.pateo.myapplication.qualifier.annotation.Test1 Test1 provideTest1(){ return new Test1(); } @Provides @com.example.pateo.myapplication.qualifier.annotation.Test2 Test2 provideTest2(){ return new Test2(); } }
@Component(modules = TestModule.class) public interface TestActivityComponent { void inject(TestActivity testActivity); }
public class TestActivity extends AppCompatActivity { Test1 testInject1; Test2 testInject2; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); DaggerTestActivityComponent.create().inject(this); ((TextView)findViewById(R.id.tv)).setText(testInject1.getStr()); } @Inject public void getTestInject1(@com.example.pateo.myapplication.qualifier.annotation.Test1 Test1 test1) { testInject1=test1; } @Inject public void getTestInject2(@com.example.pateo.myapplication.qualifier.annotation.Test2 Test2 test2) { testInject2=test2; } }
五、@lazy
懒加载标签,使用时通过get方法加载
public class TestInject { @Inject public TestInject(){} public String getStr(){ return "Test Lazy"; } }
@Component public interface TestActivityComponent { void inject(TestActivity testActivity); }
public class TestActivity extends AppCompatActivity { @Inject Lazy<TestInject> testInjects; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); DaggerTestActivityComponent.create().inject(this); ((TextView)findViewById(R.id.tv)).setText(testInjects.get().getStr()); } }