viewpager - Android obtiene fragmento que está en FragmentPagerAdapter
view pager adapter android studio (5)
Con esta función puede encontrar el fragmento por la posición del adaptador del buscapersonas.
public Fragment findFragmentByPosition(int position) {
FragmentPagerAdapter fragmentPagerAdapter = getFragmentPagerAdapter();
return getSupportFragmentManager().findFragmentByTag(
"android:switcher:" + getViewPager().getId() + ":"
+ fragmentPagerAdapter.getItemId(position));
}
Código de muestra para v4 support api.
Tengo el siguiente problema: Tengo una actividad en la que tengo dos pestañas que están hechas como fragmentos usando FragmentPagerAdapter. En algún momento me gustaría cambiar la Vista de uno de estos fragmentos, pero no puedo encontrar FragmentById () o findFragmentByTag ( ) No puedo establecer la identificación, porque no estoy declarando Fragment en XML, debido a FragmentPagerAdapter Y cuando estoy tratando de establecer la etiqueta, obtengo el siguiente problema:
08-15 21:46:23.805: E/AndroidRuntime(9297): java.lang.IllegalStateException: Can''t change tag of fragment Companies{416d7b78 id=0x7f04002e companies}: was companies now android:switcher:2130968622:1
Mi código del buscapersonas FragmentPagerAdapter :
public class TabsAdapter extends FragmentPagerAdapter implements ActionBar.TabListener, ViewPager.OnPageChangeListener {
private final FragmentActivity mContext;
private final ActionBar mActionBar;
private final ViewPager mViewPager;
private final ArrayList<TabInfo> mTabs = new ArrayList<TabInfo>();
final class TabInfo {
private final Class<?> clss;
private final Bundle args;
TabInfo(Class<?> _class, Bundle _args) {
clss = _class;
args = _args;
}
}
public TabsAdapter(SherlockFragmentActivity activity, ViewPager pager) {
super(activity.getSupportFragmentManager());
mContext = activity;
mActionBar = activity.getSupportActionBar();
mViewPager = pager;
mViewPager.setAdapter(this);
mViewPager.setOnPageChangeListener(this);
}
public void addTab(ActionBar.Tab tab, Class<?> clss, Bundle args) {
TabInfo info = new TabInfo(clss, args);
tab.setTag(info);
tab.setTabListener(this);
mTabs.add(info);
mActionBar.addTab(tab);
notifyDataSetChanged();
}
@Override
public int getCount() {
return mTabs.size();
}
@Override
public Fragment getItem(int position) {
TabInfo info = mTabs.get(position);
FragmentTransaction ft=mContext.getSupportFragmentManager().beginTransaction();
Fragment fragment=Fragment.instantiate(mContext, info.clss.getName(), info.args);
if(position==1){
ft.add(mViewPager.getId(), fragment, "companies");
}else{
ft.add(mViewPager.getId(), fragment);
}
Log.v("FRAGMENT ID", "fragment tag: "+fragment.getTag());
ft.commit();
Log.v("FRAGMENT ID", "fragment tag: "+fragment.getTag());
return fragment;
}
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
}
@Override
public void onPageSelected(int position) {
mActionBar.setSelectedNavigationItem(position);
new Thread(new Runnable() {
@Override
public void run() {
MainActivity.this.hideKeyboard();
}
}).start();
}
@Override
public void onPageScrollStateChanged(int state) {
}
@Override
public void onTabSelected(Tab tab, FragmentTransaction ft) {
Object tag = tab.getTag();
for (int i = 0; i < mTabs.size(); i++) {
if (mTabs.get(i) == tag) {
mViewPager.setCurrentItem(i);
}
}
}
@Override
public void onTabUnselected(Tab tab, FragmentTransaction ft) {
}
@Override
public void onTabReselected(Tab tab, FragmentTransaction ft) {
}
}
Gracias de antemano por sus respuestas.
Encontré una manera un poco menos grosera de manejar un Fragment
creado por un FragmentPagerAdapter
. En lugar de imitar la forma en que se crean las etiquetas, anule la instantiateItem()
, obtenga el Fragment
devuelto por la superclase y guarde la etiqueta en TabInfo
. Esto funciona para mí en API> = 15, puede funcionar con menor. Esto todavía hace algunas suposiciones sobre el código privado.
static final class TabInfo {
private final Class<?> clss;
private final Bundle args;
private String tag; // ** add this
TabInfo(Class<?> _class, Bundle _args) {
clss = _class;
args = _args;
}
}
@Override
public Object instantiateItem(ViewGroup container, int position) {
final Fragment fragment = (Fragment) super.instantiateItem(container, position);
final TabInfo info = mTabs.get(position);
info.tag = fragment.getTag(); // set it here
return fragment;
}
O en API <16, creo que instantiateItem()
toma una View()
lugar de ViewGroup()
, como esta:
public Object instantiateItem(View container, int position);
Luego permite una forma de obtener el Fragment
, manteniendo el truco contenido.
public Fragment getFragment(int index) {
return mContext.getFragmentManager().findFragmentByTag(mTabs.get(index).tag);
}
Para que funcione, la declaración de mContext
necesita cambiar a Activity
, se pasa como una Activity
todos modos:
private final Activity mContext;
Es muy tarde para responder a esta pregunta, pero he buscado mucho, nadie me dice la respuesta exacta, podría ser que alguien lo encontrara útil.
He establecido mis fragmentos a través de FragmentPagerAdapter
e hice la comunicación entre fragmentos
https://developer.android.com/training/basics/fragments/communicating.html#Deliver
siguiendo este enlace y para FindFragmentById simplemente utilicé viewpager.getId () en la mainactivity.
Los Fragmentos suministrados por FragmentPagerAdapter se etiquetan automáticamente cuando se crean instancias. Puede recuperar la etiqueta con este método:
private static String makeFragmentName(int viewPagerId, int index) {
return "android:switcher:" + viewPagerId + ":" + index;
}
Referencia: reutilización de fragmentos en un fragmento páginaradapter
Un enfoque más simple para esto es obtener las etiquetas directamente del Administrador de Fragmentos; Me gusta esto:
fm.getFragments().get(0).getTag()
Puede reemplazar la posición, según el fragmento para el que necesite la etiqueta. Espero que esto ayude a otros !.