16

I am trying to put a ViewPager2 with 2 tabs(2 fragments) within my main fragment.

My fragment class extends Fragment and I need it to contain a ViewPager2 with fragments implemented inside.
I couldn't find guides explaining this clearly on the web as all of them are being implemented within classes extending FragmentActivity and not Fragment.

For example: https://developer.android.com/training/animation/screen-slide-2#fragment

Adam Ma
  • 624
  • 5
  • 16

1 Answers1

11

ViewPager2 is an improved version of the ViewPager library that offers enhanced functionality and addresses common difficulties with using ViewPager.
Such implementations for nesting a ViewPager2 within a fragment are missing on the web as Android Developer guide shows an implementation within activity.

1) Your main fragment layout must have a ViewPager2 added to its XML file as follows:

<com.google.android.material.tabs.TabLayout
        android:id="@+id/tabs"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />
<!-- Tabs widget can be removed if you don't need tabs on top of pager-->
    <androidx.viewpager2.widget.ViewPager2
        android:id="@+id/myPager"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_below="@+id/tabs" />

2) The next step is to prepare our FragmentStateAdapter to set it as the ViewPager2 adapter:

public class ViewPagerAdapter extends FragmentStateAdapter {

    private final Fragment[] mFragments = new Fragment[] {//Initialize fragments views
//Fragment views are initialized like any other fragment (Extending Fragment)
                new FirstPagerFrag(),//First fragment to be displayed within the pager tab number 1
                new SecondPagerFrag(),
        };
        public final String[] mFragmentNames = new String[] {//Tabs names array
                "First Tab",
                "SecondTab"
        };

        public ViewPagerAdapter(FragmentActivity fa){//Pager constructor receives Activity instance
            super(fa);
    }

    @Override
    public int getItemCount() {
        return mFragments.length;//Number of fragments displayed
    }

    @Override
    public long getItemId(int position) {
        return super.getItemId(position);
    }

    @NonNull
    @Override
    public Fragment createFragment(int position) {
        return mFragments[position];
    }
}

3) Attaching the adapter to ViewPager2 This part is implemented within our fragment that contains the ViewPager2:

private ViewPager2 mViewPager;
    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);

    mViewPager = view.findViewById(R.id.queueContainer);//Get ViewPager2 view
    mViewPager.setAdapter(new ViewPagerAdapter(getActivity()));//Attach the adapter with our ViewPagerAdapter passing the host activity

    TabLayout tabLayout = view.findViewById(R.id.tabs);
    new TabLayoutMediator(tabLayout, mViewPager,
            new TabLayoutMediator.TabConfigurationStrategy() {
                @Override
                public void onConfigureTab(@NonNull TabLayout.Tab tab, int position) {
                    tab.setText(((ViewPagerAdapter)(mViewPager.getAdapter())).mFragmentNames[position]);//Sets tabs names as mentioned in ViewPagerAdapter fragmentNames array, this can be implemented in many different ways.
                }
            }
    ).attach();
}
Adam Ma
  • 624
  • 5
  • 16