📅  最后修改于: 2023-12-03 15:24:06.850000             🧑  作者: Mango
Dagger是一个开源的依赖注入框架,可用于Android和Java应用程序。在Android应用程序中,使用Dagger可以轻松管理应用程序中的依赖关系,使代码更加模块化、可维护和可测试。
首先,在项目中使用Gradle构建添加Dagger库的依赖项:
dependencies {
implementation 'com.google.dagger:dagger:2.x'
annotationProcessor 'com.google.dagger:dagger-compiler:2.x'
}
其中,x是指Dagger库的版本号。
@Module
public class MyModule {
@Provides
public MyDependency provideMyDependency() {
return new MyDependencyImpl();
}
}
其中,@Provides用于标记提供依赖的方法,MyDependency是需要提供的依赖类型,MyDependencyImpl是依赖的实现类。
@Component(modules = {MyModule.class})
public interface MyComponent {
void inject(MyActivity activity);
}
其中,@Component用于标记连接依赖的类,modules指定需要连接的Module类,inject方法用于将依赖注入到目标类中。
public class MyActivity extends AppCompatActivity {
@Inject
MyDependency myDependency;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
DaggerMyComponent.create().inject(this);
}
}
其中,@Inject用于标记需要注入依赖的属性,在onCreate方法中,通过DaggerMyComponent.create().inject(this)将依赖注入到目标类中。
在实际应用开发中,可能需要注入多个依赖,或者需要管理Scope等问题。在这种情况下,Dagger还提供了更加高级的使用方式。
可以使用Subcomponent创建子组件,并将它们绑定到父组件中的一个或多个Module。
@Singleton
@Component(modules = {ParentModule.class})
public interface ParentComponent {
ChildComponent createChildComponent(ChildModule childModule);
}
@Subcomponent(modules = {ChildModule.class})
public interface ChildComponent {
void inject(ChildActivity childActivity);
}
@Module
public class ParentModule {
@Provides
@Singleton
public MyDependency provideMyDependency() {
return new MyDependencyImpl();
}
}
@Module
public class ChildModule {
private final ChildActivity childActivity;
public ChildModule(ChildActivity childActivity) {
this.childActivity = childActivity;
}
@Provides
@ActivityScope
public MyOtherDependency provideMyOtherDependency() {
return new MyOtherDependencyImpl(childActivity);
}
}
public class ChildActivity extends AppCompatActivity {
@Inject
MyDependency myDependency;
@Inject
MyOtherDependency myOtherDependency;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_child);
ParentComponent parentComponent = DaggerParentComponent.create();
ChildComponent childComponent = parentComponent.createChildComponent(new ChildModule(this));
childComponent.inject(this);
}
}
有时会有多个相同类型的依赖需要注入,但这些依赖价格或者类型不同,这时就可以使用@Qualifier进行区分。
public interface MyComponent {
@Named("userName")
String provideUserName();
@Named("password")
String providePassword();
}
@Module
public class MyModule {
@Provides
@Named("userName")
public String provideUserName() {
return "JohnDoe";
}
@Provides
@Named("password")
public String providePassword() {
return "password";
}
}
在注入时,可以使用@Named区分需要的依赖。
public class MainActivity extends AppCompatActivity {
@Inject
@Named("userName")
String userName;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
DaggerMyComponent.create().inject(this);
}
}
通过使用@Scope,可以在一个组件中定义一个Scope,并且在提供依赖时为每个依赖创建一个实例。
@Scope
@Retention(RetentionPolicy.RUNTIME)
public @interface ActivityScope {
}
@Module
public class MyModule {
@Provides
@ActivityScope
public MyDependency provideMyDependency() {
return new MyDependencyImpl();
}
}
@Component(modules = {MyModule.class})
@ActivityScope
public interface MyComponent {
void inject(MyActivity activity);
}
public class MainActivity extends AppCompatActivity {
@Inject
MyDependency myDependency1;
@Inject
MyDependency myDependency2;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
DaggerMyComponent.create().inject(this);
}
}
其中,@Scope用于声明Scope,可以在Module和Component中使用。在MyModule中,使用@ActivityScope声明提供的依赖需要在同一Activity中共享实例。在MyComponent中,使用@ActivityScope声明Component创建的所有依赖都可以共享该实例。
注意:在使用自定义Scope时,需要保证该Scope是在运行时保持不变的,如果Component中声明的Scope与Module中声明的Scope不一致,会报错。
Dagger是一个非常强大的依赖注入框架,使用Dagger可以简化Android应用程序中的依赖管理。在开发过程中,根据需求灵活地运用Dagger的高级用法,可以使代码更加模块化、可维护和可测试。