私が持っているエラーは次のとおりです:
原因:Java.lang.IllegalArgumentException:クラスにバインドされたインジェクターファクトリがありません。インジェクターファクトリは、MyActivity_:[MyActivity]のスーパータイプにバインドされていました。サブタイプのインジェクターファクトリをバインドするつもりでしたか?
私が理解しているように、それはAndroidAnnotationsライブラリを使用しているために起こります。
AppComponent.class:
@Singleton
@Component(modules = {
AndroidInjectionModule.class,
AppModule.class,
ActivityBindingModule.class })
public interface AppComponent extends AndroidInjector<DaggerApplication> {
@Component.Builder
interface Builder {
@BindsInstance Builder application(Application application);
AppComponent build();
}
void inject(Application application);
@Override
void inject(DaggerApplication instance);
}
AppModule.class:
@Module
public abstract class AppModule {
@Binds
abstract Context provideContext(Application application);
@Provides
@Singleton
static SharedPreferencesManager providesPreferences(Application application){
return SharedPreferencesManager_.getInstance_(application);
}
}
ActivityBindingModule.class:
@Module
public abstract class ActivityBindingModule {
@ContributesAndroidInjector(modules = LoginActivityModule.class)
@LoginActivityScope
abstract LoginActivity bindLoginActivity();
}
Application.class:
@EApplication
public class Application extends DaggerApplication {
@Inject
DispatchingAndroidInjector<Activity> activityDispatchingAndroidInjector;
protected AndroidInjector<? extends DaggerApplication> applicationInjector() {
AppComponent appComponent = DaggerAppComponent.builder()
.application(this)
.build();
appComponent.inject(this);
return appComponent;
}
}
LoginActivityModule.class
@Module
public class LoginActivityModule {
@Provides
@LoginActivityScope
@ActivityContext
public Context providesContext(LoginActivity loginActivity){
return loginActivity;
}
@Provides
@LoginActivityScope
public LoginViewModel providesLoginViewModel(TelephonyManager telephonyManager,
LoginModel loginModel,
SharedPreferencesManager sharedPreferencesManager,
LoginRemoteRepository loginRemoteRepository){
return new LoginViewModel(telephonyManager, loginModel, sharedPreferencesManager, loginRemoteRepository,
new CompositeSubscription());
}
@Provides
@LoginActivityScope
public LoginRemoteRepository providesRemoteRepository(@ActivityContext Context context,
MainApi mainApi,
SharedPreferencesManager sharedPreferencesManager){
return new LoginRemoteRepository(mainApi, sharedPreferencesManager, context.getContentResolver());
}
@Provides
@LoginActivityScope
public LoginModel provideLoginModel(){
return new LoginModel();
}
@Provides
@LoginActivityScope
public TelephonyManager provideTelephonyManager(Context context){
return (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
}
}
LoginActivity.class:
@EActivity(R.layout.activity_login)
public class LoginActivity {
@Inject
LoginViewModel loginViewModel;
@AfterViews
void afterViews(){
AndroidInjection.inject(this);
}
}
十分な情報に基づく推測:AndroidAnnotationsを使用すると、クラスが実際に別の方法で呼び出されるために発生する可能性があります(アンダースコアがどこかに追加されています)。次に、同様にバインディングを定義する必要があります(アンダースコアがどこにあるかわかりません)。
@ContributesAndroidInjector(modules = LoginActivityModule_.class)
@LoginActivityScope
abstract LoginActivity bindLoginActivity();
Dagger 2エラーの処理方法:「インジェクタファクトリは...のスーパータイプにバインドされました。サブタイプのインジェクタファクトリをバインドすることを意味しましたか?」
いくつかのBaseActivityがあるとします。
open class BaseActivity : MvpAppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
AndroidInjection.inject(this)
super.onCreate(savedInstanceState)
}
}
また、ActivityBuilderモジュール(BaseActivity自体を提供する)もあり、BaseActivityを正常に実行するために必要な依存関係を提供するモジュールもあります。
@Module
abstract class ActivityBuilder {
@ContributesAndroidInjector(modules = [BaseModule::class])
abstract fun bindBaseActivity(): BaseActivity
}
そのようなChildActivityを追加する場合
クラスChildActivity:BaseActivity(){}
「ねえ、ダガー2はBaseActivityの依存関係を満たし、それを拡張しているので、ChildActivityを起動して実行しますよね?」違う。 「インジェクタファクトリがスーパータイプの...にバインドされました...サブタイプのインジェクタファクトリをバインドするつもりでしたか?」という例外が発生します。
a)AndroidInjection.inject(this)をChildActivity onCreate()メソッドに追加します。
class ChildActivity : BaseActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
AndroidInjection.inject(this)
super.onCreate(savedInstanceState)
}
}
b)BaseActivityのすべてのサブクラスをActivityBuilderモジュール(アクティビティを提供する)に追加します。 BaseActivityの依存関係を満たすBaseModuleも、子クラス(ChildActivity)の@ContributesAndroidInjectorに含める必要があることに注意してください。
@Module
abstract class ActivityBuilder {
@ContributesAndroidInjector(modules = [BaseModule::class])
abstract fun bindBaseActivity(): BaseActivity
//Adding subclasses
@ContributesAndroidInjector(modules = [BaseModule::class])
abstract fun bindChildActivity(): ChildActivity
}