【问题标题】:Inject the same instance of a scoped object multiple times多次注入同一个作用域对象实例
【发布时间】:2018-05-28 21:30:53
【问题描述】:

我有一个 Activity 和它的 Presenter,它们都被注入了一个 Adapter。 Activity 需要在 RecyclerView 上设置适配器,并且 Presenter 需要它在数据发生变化时调用更新方法(例如:notifyItemChanged)。

问题是因为适配器被注入了两次,所以演示者和活动没有相同的实例。我需要 Dagger 来创建它的一个实例。但是,Adapter 需要 Activity 的上下文并且有 @ActivityScope 来防止内存泄漏,这意味着我不能同时在其上使用 @Singleton 范围。

有什么我不明白的吗?有没有办法在两个类中注入适配器,而无需在演示者或活动中使用setAdapter 方法手动设置它?或者有没有办法限制创建的 Adapter 实例的数量?

编辑:依赖注入文件:

@Module
public interface MainModule {

    @ActivityContext @Binds
    Context context(MainActivity activity);

    @ActivityScope @Binds
    MainContract.Presenter presenter(MainPresenter presenter);

    // CHILD FRAGMENT
    @FragmentScope @ContributesAndroidInjector
    ChildFragment childFragment();

    @ActivityScope @Binds
    ChildContract.Presenter childPresenter(ChildPresenter presenter);

    @ActivityScope @Binds
    ChildContract.AdapterView adapterView(MyAdapter adapter);

}

ChildFragmentChildPresenterMyAdapter 类使用 @ActivityScope 注释。

这是我让它工作的唯一方法,对我来说似乎是错误的,因为 ChildPresenter 和 MyAdapter 仅在片段中使用。但是,用@FragmentScope 注释它们会引发错误:“可能不引用具有不同范围的绑定”。另外,片段“提供者”和片段本身是用两个不同的范围注释的?

【问题讨论】:

  • 使用@ActivityScope 有什么问题?
  • 没什么,但我不能拥有这个范围,而且@Singleton 也不能限制为一个实例。
  • 为什么需要限制为一个实例? Presenter、Adapter 和 Activity 都应该在@ActivityScope—问题已解决。如果你想保存一些状态,你可以创建一些 @Singleton Repository 或保存数据等的东西
  • 他们都已经在@ActivityScope。我的适配器没有状态,我的演示者有。因为presenter提供数据并更新adapter,所以更新和显示的必须是同一个实例,所以我只需要一个实例。
  • 相信你对示波器有错误的印象。作用域对象在其作用域中存在一次。如果一切都是活动范围的,那么每个活动将只有一个。

标签: android android-adapter dagger-2 android-mvp


【解决方案1】:

MVP 架构中,presenter 应该只关心业务逻辑。这意味着 presenter 对 Android 的东西一无所知,并且不包含任何 Android 特定项目。

在您的情况下,您写道您的 presenter 拥有一个 适配器 并在其上调用 notifyItemChanged 方法。这是一个特定于 Android 的项目,不应以这种方式工作。 view 负责持有 adapter,从 presenteradapter 的任何交互都应该通过视图

这对您的示例意味着什么:

  • 视图创建并保存一个适配器
  • 视图接口提供(和活动实现)调用notifyAdapterItemChanged
  • presenter 需要告诉 adapter 数据已更新时,它会调用 view notifyAdapterItemChanged(以及 view 依次调用 适配器

旁注:如果您需要相反的方式提供数据(从适配器到演示者),我建议向演示者添加一个特殊的适配器接口,您可以将其作为适配器中的弱引用保留。 em>

希望对您有所帮助,如果您有任何其他问题,请告诉我...

【讨论】:

  • 我没有明确提到它,但是我的适配器使用AdapterView 之类的方法实现了我的AdapterView 接口,因此演示者没有android 项目。 Adapter 通过回调向 Presenter 提供数据。但我会试试你的方法。
  • 我确实需要反过来传递数据,但为什么是 WeakReference?我在绑定演示者时设置了一个回调,然后在未绑定时将其删除,可以吗?
  • 是的,这也有效。当我通过接口授予对演示者的访问权限时,我更喜欢使用弱引用,因为它不会阻塞 GC。但你的方式肯定也行得通……
猜你喜欢
  • 1970-01-01
  • 2023-01-29
  • 1970-01-01
  • 2023-03-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-04-04
相关资源
最近更新 更多