【问题标题】:How to access the host fragment from ViewPager page fragment using Navigation Architecture Components如何使用导航架构组件从 ViewPager 页面片段访问主机片段
【发布时间】:2020-10-20 22:45:01
【问题描述】:

我有一个项目要迁移到Navigation Architecture Components

在迁移之前,我有一个活动,其中有一个片段,该片段承载ViewPager;我可以通过引用我在片段事务中设置的主机片段标记从ViewPager 适配器片段访问此片段中的方法:

MyFragment fragment = (MyFragment ) ((MyActivity) requireActivity())
        .getSupportFragmentManager().findFragmentByTag("fragment_tag"); 
fragment.someMethodInMyFragment();

这是一个欺骗部分迁移的图表,以及我需要通过黄色箭头访问的内容:

在导航组件中,我没有找到机会to set a tag 到承载ViewPager 的目标片段,因此我可以像以前一样通过标签访问它。此外,ViewPager 适配器片段不是导航组件的一部分。

我尝试过的:ViewPager 适配器片段中:

尝试 1

MyFragment fragment = (MyFragment) getParentFragment(); // This returns the navigation host fragment. So ClassCastException is raised
fragment.someMethodInMyFragment();

尝试 2

MyFragment fragment = (MyFragment) requireActivity().getSupportFragmentManager()
     .findFragmentById(R.id.myFragment); // id of myFragment in the nav graph.
fragment.someMethodInMyFragment(); // fragment is null

更新:

发帖ViewPager适配器

public class PageFragmentPagerAdapter extends FragmentStatePagerAdapter {

    public PageFragmentPagerAdapter(FragmentManager fm) {
        super(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT);
    }

    @NonNull
    @Override
    public Fragment getItem(int position) {
        return MyPagerFragment.newInstance(position);
    }


    @Override
    public int getCount() {
        return 10;
    }

}

我在MyFragment 中设置了 ViewPager,如下所示

public class MyFragment extends Fragment {
    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);
        ViewPager viewPager = view.findViewById(R.id.viewpager);
        PageFragmentPagerAdapter adapter = new PageFragmentPagerAdapter(requireActivity()
                                                   .getSupportFragmentManager());
        viewPager.setAdapter(adapter);
    }

【问题讨论】:

  • 你为什么要做这些而不是直接将你的Fragment 传递给你的适配器?您可以控制适配器的构造函数,并且可以随意传递它。
  • @ianhanniballake 所以,我需要将MyFragment 作为适配器参数传递,然后通过getItem() 将其传递给适配器的片段。我会试试这个。得不到太多。我发布了适配器和片段代码,如果这样更清楚的话..谢谢
  • 你为什么要传递 requireActivity().getSupportFragmentManager() 而不是 getChildFragmentManager() (传递总是正确的)?

标签: android android-fragments android-viewpager android-navigation


【解决方案1】:

您的问题是您使用requireActivity().getSupportFragmentManager() 作为适配器的FragmentManager

相反,对于完全包含在另一个片段中的片段,您应该始终使用getChildFragmentManager() - 您会注意到,在配置更改或进程死亡和重新创建时,这是正确恢复每个片段的状态所必需的。

当您使用子 FragmentManager 时,requireParentFragment() 将返回您正在寻找的正确片段。

【讨论】:

  • 谢谢你,不幸的是,当我为返回的片段尝试getChildFragmentManager().findFragmentById(R.id.myFragment) 时,这引发了 NPE ..
  • 就像我的回答说的那样,您只需在您的 ViewPager 片段之一中使用requireParentFragment()(因为这是您使用父级的子级 FragmentManager 设置它的父级)
  • 现在是java.lang.IllegalStateException: Fragment PagerFragment{3a76a43} (73d6dd69-0f1a-4428-8c8e-055a24fe61ae) id=0x7f0800f8} is not a child Fragment, it is directly attached to com.xx.MainActivity@e045857
  • 那你还没有把你的适配器改成使用getChildFragmentManager()
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-03-29
  • 1970-01-01
  • 2018-10-23
  • 2018-11-18
  • 1970-01-01
  • 2019-06-14
  • 1970-01-01
相关资源
最近更新 更多