To avoid finding fragment with the hard-coded tag f$id
set internally which might be changed by Google in any future release:
Method 1: filtering the page fragments with the resumed one
Assuming the page fragment of the ViewPager2
is PageFragment
, then you can find the current ViewPager
fragment in the current fragmentManager fragments
and check if it is in the resumed state (currently displayed on the screen)
val fragment = supportFragmentManager.fragments
.find{ it is PageFragment && it.isResumed } as PageFragment
Note: supportFragmentManager
should be replaced with childFragmentManager
if the ViewPager
is a part of a Fragment.
For java (API 24+):
Fragment fragment =
getSupportFragmentManager().getFragments().stream()
.filter(it -> it instanceof PageFragment && it.isResumed())
.collect(Collectors.toList()).stream().findFirst().get();
Method 2: setting some argument to the PageFragment, and filter fragments based on it
Kotlin:
Adapter
class MyAdapter(fragmentManager: FragmentManager, lifecycle: Lifecycle) :
FragmentStateAdapter(fragmentManager, lifecycle) {
//.... omitted
override fun createFragment(position: Int): Fragment
= PageFragment.getInstance(position)
}
PageFragment:
class PageFragment : Fragment() {
//.... omitted
companion object {
const val POSITION = "POSITION";
fun getInstance(position: Int): PageFragment {
return PageFragment().apply {
arguments = Bundle().also {
it.putInt(POSITION, position)
}
}
}
}
}
And filter with the position argument to get the needed PageFragment:
val fragment = supportFragmentManager.fragments.firstOrNull {
it is PageFragment && it.arguments?.getInt("POSITION") == id } // id from the viewpager >> for instance `viewPager.currentItem`
Java (API 24+):
Adapter:
class MyAdapter extends FragmentStateAdapter {
// .... omitted
@NonNull
@Override
public Fragment createFragment(int position) {
return PagerFragment.newInstance(position);
}
}
PageFragment:
public class PagerFragment extends Fragment {
// .... omitted
public static Fragment newInstance(int position) {
PagerFragment fragment = new PagerFragment();
Bundle args = new Bundle();
args.putInt("POSITION", position);
fragment.setArguments(args);
return fragment;
}
}
And to get a fragment of a certain viewPager
item:
Optional<Fragment> optionalFragment = getSupportFragmentManager().getFragments()
.stream()
.filter(it -> it instanceof PagerFragment && it.getArguments() != null && it.getArguments().getInt("POSITION") == id)
.findFirst();
optionalFragment.ifPresent(fragment -> {
// This is your needed PageFragment
});