简体   繁体   English

Dagger 2-提供应用程序类

[英]Dagger 2 - Providing Application class

I am trying to use Dagger 2 to inject my application class, MyApplication as I use it in various places. 我正在尝试使用Dagger 2注入我的应用程序类MyApplication因为我在各种地方都使用了它。 This is my setup using Dagger 2.11 这是我使用Dagger 2.11设置

MyApplication.java MyApplication.java

public class MyApplication extends Application  implements HasActivityInjector {

  @Inject
  DispatchingAndroidInjector<Activity> dispatchingAndroidInjector;

  @Override
  public void onCreate() {
    super.onCreate();
    AppInjector.init(this);
  }

  @Override
  public DispatchingAndroidInjector<Activity> activityInjector() {
    return dispatchingAndroidInjector;
  }
}

AppInjector.java AppInjector.java

public class AppInjector {

  public static void init(MyApplication application){

    //Initialize dagger and inject the application
    DaggerAppComponent.builder().application(application).build().inject(application);

    application.registerActivityLifecycleCallbacks(new Application.ActivityLifecycleCallbacks() {
      @Override
      public void onActivityCreated(Activity activity, Bundle aBundle) {
        handleActivity(activity);
      }

      @Override
      public void onActivityStarted(Activity activity) {

      }

      @Override
      public void onActivityResumed(Activity activity) {

      }

      @Override
      public void onActivityPaused(Activity activity) {

      }

      @Override
      public void onActivityStopped(Activity activity) {

      }

      @Override
      public void onActivitySaveInstanceState(Activity activity, Bundle aBundle) {

      }

      @Override
      public void onActivityDestroyed(Activity activity) {

      }
    });
  }

  private static void handleActivity(Activity activity){
    if(activity instanceof HasSupportFragmentInjector ){
        AndroidInjection.inject(activity);
    }
    if (activity instanceof FragmentActivity){
      ((FragmentActivity) activity).getSupportFragmentManager()
              .registerFragmentLifecycleCallbacks(
                      new FragmentManager.FragmentLifecycleCallbacks() {
                        @Override
                        public void onFragmentCreated(FragmentManager fm, Fragment f,
                                                      Bundle savedInstanceState) {
                          if (f instanceof Injectable) {
                            Log.i("LifecycleCallbacks", "injected:" + f);

                            AndroidSupportInjection.inject(f);
                          }
                        }
                      }, true);
    }
  }

AppComponent.java AppComponent.java

@Singleton
@Component(modules = {
        AndroidInjectionModule.class,
        ActivityBuilder.class,
        AppModule.class
})

public interface AppComponent {
  @Component.Builder
  interface Builder {
    @BindsInstance Builder application(Application application);
    AppComponent build();
  }

  void inject(MyApplication application);
}

However, every time I try use @Inject MyApplication application in a constructor, dagger throws an error that it has no way to provide it without an @Provides 但是,每次我尝试在构造函数中使用@Inject MyApplication application时,dagger都会抛出一个错误,即如果没有@Provides,它就无法提供它。

Furthure more, I am not sure I should be using the Application everywhere, and rather only its Context ? 更进一步,我不确定是否应该在所有地方都使用该应用程序,而不仅仅是它的Context If so, how would I provide the Context ? 如果是这样,我将如何提供Context

Have a look at your Builder... 看看您的Builder ...

@Component.Builder
interface Builder {
--> @BindsInstance Builder application(Application application);
    AppComponent build();
}

All Dagger knows about is your Application , you're never mentioning MyApplication , hence injecting it will fail. Dagger所知道的只是您的Application ,您永远不会提到MyApplication ,因此注入它会失败。


I don't know why you'd have to inject MyApplication specifically, but the easiest solution would be to change it to bind your MyApplication instead... 我不知道为什么您必须专门注入MyApplication ,但是最简单的解决方案是将其更改为绑定MyApplication

@Component.Builder
interface Builder {
    @BindsInstance Builder application(/** --> */ MyApplication application);
    AppComponent build();
}

Then Dagger knows about MyApplication but not of Application . 然后Dagger知道MyApplication但不知道Application To fix this, you can just add a module that binds the other types which is easy enough because you have the subtype...eg 为了解决这个问题,您可以添加一个绑定其他类型的模块,这很容易,因为您拥有子类型...例如

@Module interface AppModule { // could also be an abstract class
  @Binds Application bindApplication(MyApplication application);

  // if you also want to bind context
  @Binds Context bindContext(MyApplication application);
}

And just add this module to your component. 并将此模块添加到您的组件中。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM