如何使用Dagger2将Activity注入到Fragment中

3
我希望您能够将我的MainActivity注入到Fragment中进行翻译。我有一个接口在MainActivity中实现,用于监听来自Fragment的事件。因此,我想注入MainActivity并在其上调用事件侦听器。
我尝试了以下方法,但未能成功。以下是代码片段:
接口
public interface RecipeItemListener {
    void onRecipeItem();
}

实现接口的MainActivity

public class MainActivity extends AppCompatActivity implements RecipeItemListener {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        if(savedInstanceState == null) {
            getSupportFragmentManager()
                    .beginTransaction()
                    .add(R.id.main_fragment_container, RecipeListView.newInstance(), RecipeListView.TAG)
                    .commit();
        }
    }

    @Override
    public void onRecipeItem() {
        Timber.d("onRecipeItem");
    }
}

我的模块提供了MainActivity

@Module
public class RecipeListModule {
    private MainActivity mainActivity;

    public RecipeListModule(MainActivity mainActivity) {
        this.mainActivity = mainActivity;
    }

    @RecipeListScope
    @Provides
    public RecipeItemListener providesRecipeListMainActivity() {
        return mainActivity;
    }
}

我的主要组件

@Singleton
@Component(modules = {
        AndroidModule.class,
        NetworkModule.class})
public interface BusbyBakingComponent {
    RecipeListComponent add(RecipeListModule recipeListModule);
}

我的子组件

@RecipeListScope
@Subcomponent(modules = {RecipeListModule.class})
public interface RecipeListComponent {
    void inject(RecipeListView target);
}

我的应用程序类

public class BusbyBakingApplication extends Application {
    private BusbyBakingComponent applicationComponent;
    private RecipeListComponent recipeListComponent;

    @Override
    public void onCreate() {
        super.onCreate();

        applicationComponent = createApplicationComponent();
    }

    public BusbyBakingComponent createApplicationComponent() {
        return DaggerBusbyBakingComponent.builder()
                .networkModule(new NetworkModule())
                .androidModule(new AndroidModule(BusbyBakingApplication.this))
                .build();
    }

    public BusbyBakingComponent getApplicationComponent() {
        return applicationComponent;
    }

    public RecipeListComponent createRecipeListComponent(MainActivity activity) {
        recipeListComponent = applicationComponent.add(new RecipeListModule(activity));
        return recipeListComponent;
    }

    public void releaseRecipeListComponent() {
        recipeListComponent = null;
    }
}

在我的代码片段中,我尝试进行如下注入:

@Inject MainActivity mainActivity;
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    ((BusbyBakingApplication)getActivity().getApplication())
            .createRecipeListComponent((MainActivity)getActivity())
            .inject(RecipeListView.this);
}

我不断收到以下错误信息:
Error:(14, 8) error: [me.androidbox.busbybaking.di.RecipeListComponent.inject(me.androidbox.busbybaking.recipieslist.RecipeListView)] me.androidbox.busbybaking.recipieslist.MainActivity cannot be provided without an @Inject constructor or from an @Provides- or @Produces-annotated method.
me.androidbox.busbybaking.recipieslist.MainActivity is injected at
me.androidbox.busbybaking.recipieslist.RecipeListView.mainActivity
me.androidbox.busbybaking.recipieslist.RecipeListView is injected at
me.androidbox.busbybaking.di.RecipeListComponent.inject(target)

非常感谢您的建议。

2
你不是已经使用 getActivity() 在片段中获取了活动吗? - EpicPandaForce
2个回答

2

如果您查看您的模块

@RecipeListScope
@Provides
public RecipeItemListener providesRecipeListMainActivity() {
    return mainActivity;
}

你提供了接口(这很好),而不是实现类MainActivity
因为你请求MainActivity
@Inject MainActivity mainActivity;

您收到了这个错误:

MainActivity无法提供[...]

因为您只提供了RecipeItemListener


请将您的代码从在RecipeListView中需要MainActivity,改为

@Inject RecipeItemListener recipeListener;

如果您的其余设置正确,那么它应该可以正常工作。


那个修复起作用了。我想注入的原因是我想从由Activity托管的Fragment中调用实现接口的MainActivity中的方法。我猜我本可以在onAttach方法中将Activity传递给Fragment。然而,我认为注入是更好的选择。 - ant2009

-1

你可以使用getActivity()在Fragment中访问activity,并将其转换为你的接口监听器,像这样:

((RecipeItemListener)getActivity()).doSomethingOnListener()

更简单,没有任何不必要的注入


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接