Getting the current Fragment instance in the viewpager
by selecting an option, I need to update the fragment that is
currently visible.
A simple way of doing this is using a trick related to the FragmentPagerAdapter
implementation:
case R.id.addText:
Fragment page = getSupportFragmentManager().findFragmentByTag("android:switcher:" + R.id.pager + ":" + ViewPager.getCurrentItem());
// based on the current position you can then cast the page to the correct
// class and call the method:
if (ViewPager.getCurrentItem() == 0 && page != null) {
((FragmentClass1)page).updateList("new item");
}
return true;
Please rethink your variable naming convention, using as the variable name the name of the class is very confusing(so no ViewPager ViewPager
, use ViewPager mPager
for example).
How to get fragment reference from ViewPager
Use viewPager.getAdapter.getItem(position);
from your Activity
or parent Fragment
.
Description (Modified) - As you wrote addFragment()
adds a fragment to mFragmentList
and you are adding fragment by this method too by calling:
mSectionsPageAdapter.addFragment(new MyChatsFragment())
And getItem()
returns a fragment from mFragmentList
where you added your fragment. So if you want to get MyChatsFragment
reference just use:
MyChatsFragment myChatsFragment = (MyChatsFragment)
mSectionsPageAdapter .getItem(position);
or
MyChatsFragment myChatsFragment = (MyChatsFragment)
viewPager.getAdapter.getItem(position);
How to get Current Fragment in ViewPager2
- Create property in your adapter to save all your fragments
- Save current position
- Get fragment from fragment list (property) by position when you need it
Something like this:
val fragments: MutableList<Fragment> = mutableListOf()
private val config: TribunConfig?
override fun createFragment(position: Int): Fragment {
val fragment = TribunNewsFragment.newInstance(if (menuTribun!!.get(position) == "News") "home"
else menuTribun!!.get(position)!!.replace(" ", "").toLowerCase(), config)!!
fragments.add(fragment)
return fragment
}
Parent:
yourTabLayout.addOnTabSelectedListener(object : TabLayout.OnTabSelectedListener {
override fun onTabSelected(tab: TabLayout.Tab?) {
val fragment = adapter.fragments[tab!!.position]
// cast fragment to your fragment class and do what you want
}
override fun onTabUnselected(tab: TabLayout.Tab?) {
}
override fun onTabReselected(tab: TabLayout.Tab?) {
}
})
Also you can use when
or if-else
for your fragments position or create base class with methods you need and cast getting fragment to it.
How to get current Fragment name in viewpager?
Inside CustomTabLayout
add
tabLayout.addOnTabSelectedListener(new TabLayout.OnTabSelectedListener()
{
@Override
public void onTabSelected(TabLayout.Tab tab)
{
int position = tab.getPosition();
}
@Override
public void onTabUnselected(TabLayout.Tab tab) {
}
@Override
public void onTabReselected(TabLayout.Tab tab) {
}
});
How to get elements of fragments created by ViewPager in MainActivity?
Unfortunately the only "safe" way to do it is to check the source code of FragmentPagerAdapter
, and see what tag
is the fragment is added with - because findFragmentByTag
is the only safe way to get a Fragment from a FragmentManager.
Of course, we need to hope that this implementation detail doesn't change between support library versions, but it actually hasn't changed in years :)
Anyways, so FragmentPagerAdapter says:
// Do we already have this fragment?
String name = makeFragmentName(container.getId(), itemId);
Fragment fragment = mFragmentManager.findFragmentByTag(name);
So what is name
?
private static String makeFragmentName(int viewId, long id) {
return "android:switcher:" + viewId + ":" + id;
}
What is viewId
and what is id
?
ViewId is container.getId()
, where container
is the ViewPager
itself.
id
is: final long itemId = getItemId(position);
which by default is return position;
.
So you can find the Fragment as follows:
Fragment fragment = fragmentManager.findFragmentByTag("android:switcher:" + viewPager.getId() + ":" + fragmentPosition);
// if fragment is null, it was not created yet by ViewPager
NOTE:
It is worth noting that you should NOT rely on getItem(int position) {
to return the same fragment instance as you passed in, because that will lead you to this problem. (This question does it correctly, the getItem()
method must always return a new Fragment instance.)
How to get the current fragment displayed in a specific tab of a viewpager?
First define a SparseArray
in your ViewPagers
' adapters like below. In this array we'll hold the instance of fragments.
SparseArray<Fragment> registeredFragments = new SparseArray<>();
And Override your Adapters' instantiateItem
method.
@Override
public Object instantiateItem(ViewGroup container, int position) {
Fragment fragment = (Fragment) super.instantiateItem(container, position);
registeredFragments.put(position, fragment);
return fragment;
}
Also Override destroyItem
method of your ViewPagers
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
registeredFragments.remove(position);
super.destroyItem(container, position, object);
}
And define a new method to get your ViewPager
Fragments
instance.
public Fragment getRegisteredFragment(int position) {
return registeredFragments.get(position);
}
And finally set add a PageChangeListener
to your ViewPagers
:
viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
}
@Override
public void onPageSelected(int position) {
// Here's your instance
YourFragment fragment =(YourFragment)yourPagerAdapter.getRegisteredFragment(position);
}
@Override
public void onPageScrollStateChanged(int state) {
}
});
I hope this'll help you. Good luck.
Edit: I'm sorry i cannot understand exactly what you're planning to do but if you need to keep sub fragment (b_1, b_2) instance you can define a method to your activity such as
public void setCurrentFragment(Fragment fragment){
this.currentFragment = fragment;
}
and in your sub view pager's adapter you can call this method like below:
subViewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
}
@Override
public void onPageSelected(int position) {
// Here's your instance
YourFragment fragment =(YourFragment)yourSubPagerAdapter.getRegisteredFragment(position);
((MyActivity)getActivity).setCurrentFragment(fragment);
}
@Override
public void onPageScrollStateChanged(int state) {
}
});
With this way you can keep one instance and your top fragment.
Related Topics
Capture Image from Camera and Display in Activity
Making Textview Scrollable on Android
How to Use Getdownloadurl in Recent Versions
Android Accelerometer Accuracy (Inertial Navigation)
How to Send a Json Object Over Request With Android
How to Display a Toast from a Background Thread on Android
Scrollview Vertical and Horizontal in Android
How to Implement Onfragmentinteractionlistener
Changing API Level Android Studio
"Failed to Load Ad: 3" With Doubleclick
"Cannot Resolve Symbol R" in Android Studio
How to Open a Url in Android'S Web Browser from My Application
Example: Communication Between Activity and Service Using Messaging
Android Check Internet Connection
Notification Bar Icon Turns White in Android 5 Lollipop
Android Studio Adds Unwanted Permission After Running Application on Real Device
Converting a View to Bitmap Without Displaying It in Android