我根据谷歌sample
使用依赖注入我可以传递的唯一外部依赖是通过AppComponent构建器
@Singleton
@Component(modules = {
AndroidInjectionModule.class,
AppModule.class,
MainTabActivityModule.class,
CoreActivityModule.class
})
public interface AppComponent {
@Component.Builder
interface Builder {
@BindsInstance
Builder application(Application application);
AppComponent build();
}
void inject(MyApplication myApplication);
}
并像这样在应用程序中注入
@Override
public void onCreate() {
super.onCreate();
DaggerAppComponent
.builder()
.application(myApplication)
.build().inject(myApplication);
...
}
根据Activity中注入的文件看起来像这样。我添加了我想要实现的目标。
public class YourActivity extends Activity {
public void onCreate(Bundle savedInstanceState) {
AndroidInjection
//.builder() THIS IS WHAT I WANT TO ACHIEVE
//.addActivityContext(this) THIS IS WHAT I WANT TO ACHIEVE
//.build() THIS IS WHAT I WANT TO ACHIEVE
.inject(this);
super.onCreate(savedInstanceState);
}
}
但问题是如何向subComponent添加其他参数。
@Subcomponent
public interface CoreActivitySubComponent extends AndroidInjector<CoreAppActivity> {
// @Subcomponent.Builder
// interface Builder {
// Builder addContext(Context context) //did not work
// CoreActivitySubComponent build(); //did not work
// }
//==or using abstract class
// in this option I do not know where to add parameter to this builder
@Subcomponent.Builder
public abstract class Builder extends AndroidInjector.Builder<CoreAppActivity> {
}
}
答案 0 :(得分:0)
问题在于Dagger 2.1.0方法 AndroidInjection.inject(this); 应该在Activity和Fragment中使用,不提供任何构建器来添加外部依赖。
我想创建一个依赖于Activity / Fragment上下文的通用模块。
样品:
public class ToastController {
private Context context;
@Inject
public ToastController(Context context) {
this.context = context;
}
public void showToast(@StringRes int res) {
Toast.makeText(context, context.getText(res), Toast.LENGTH_SHORT).show();;
}
}
但我无法将其概括到某个级别,我只能提供一个上下文模块,而是我必须为使用此模块的每个Activity / Fragment创建绑定模块。
@Singleton
@Component(modules = {
AndroidInjectionModule.class,
AppModule.class,
MainTabActivityModule.class,// IMPORTANT CLASS
})
public interface AppComponent {
@Component.Builder
interface Builder {
@BindsInstance
Builder application(Application application);
AppComponent build();
}
void inject(MyApplication myApplication);
}
这是一个地方,我为每个活动提供上下文模块
@Module
public abstract class MainTabActivityModule
@ContributesAndroidInjector(modules = ContextMainTabActivityModule.class)//THIS MODULE
abstract MainTabActivity contributeMainActivity();
}
使用@Binds注释提供和Context
@Module
public abstract class ContextMainTabActivityModule {
@Binds
abstract Context provideContext(MainTabActivity featureActivity);
}
=====================
可以通过根据sample
重写方法seedInstance来完成我试过这个,但它对我不起作用
@Subcomponent.Builder
public abstract class Builder extends AndroidInjector.Builder<CoreAppActivity> {
abstract Builder addContextModule(ContextModule contextModule);
@Override
public void seedInstance(CoreAppActivity instance) {
addContextModule(new ContextModule(instance));
}
}
下一堂课
@Module
public class ContextModule {
private CoreAppActivity coreAppActivity;
@Provides
Context getContext() {
return coreAppActivity.getBaseContext();
}
public ContextModule(CoreAppActivity coreAppActivity) {
this.coreAppActivity = coreAppActivity;
}
}
答案 1 :(得分:0)
您是否将ContextModule
添加到与this answer类似的@Subcomponent
?
我认为你的@Subcomponent
应该是这样的:
@Subcomponent(module = {ContextModule.class})
interface MainTabActivityComponent extends AndroidInjector<CoreAppActivity> {
@Subcomponent.Builder
public abstract class Builder extends AndroidInjector.Builder<CoreAppActivity> {
abstract Builder addContextModule(ContextModule contextModule);
@Override
public void seedInstance(CoreAppActivity instance) {
addContextModule(new ContextModule(instance));
}
}
}
最后不要忘记在绑定模块中包含此@Subcomponent
。
最后一个问题:这真的需要吗?
我发现使用Application
以及Activities
和Fragments
上的AndroidInjector会在我注入时给出正确的对应Context
。