android android-actionbar android-viewpager android-listfragment

Android, Cómo mezclar ActionBar.Tab+Ver buscapersonas+ListFragment



android-actionbar android-viewpager (3)

Puede intentar incluir el siguiente código en su FragmentPagerAdapter y ver si esto resuelve el problema.

public int getItemPosition(Object object) { return POSITION_NONE; }

También podría intentar usar un FragmentStatePagerAdapter .

¡He intentado probar cómo mezclar todas estas cosas y estoy teniendo problemas! Solo quiero una aplicación con tres pestañas usando ActionBar.Tab. Por ejemplo, estas pestañas pueden ser géneros de películas Acción, Aventura y Animación, el usuario puede deslizarse por las pestañas, por lo que utilizará ViewPager y cada pestaña mostrará una lista de películas de ese género. No es necesario tener tres clases de fragmentos diferentes porque todas las pestañas tendrán el mismo formato, una lista simple. Y estoy teniendo problemas porque cuando selecciono la segunda pestaña, la posición de onPageSelected es 1,

mViewPager = (ViewPager) findViewById(R.id.pager); mViewPager.setAdapter(mCollectionPagerAdapter); mViewPager.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() { @Override public void onPageSelected(int position) { mActionBar.setSelectedNavigationItem(position); } });

Esto hace que la llamada al método public Fragment getItem (int i) dentro de la clase CollectionPagerAdapter, pero luego el valor de i es 2 NOT 1, entonces llama al createView para la clase TabFragment con un valor de 2 NOT 1, por lo que las pestañas no están refrescando con éxito.

¡¡Cualquier ayuda será muy apreciada!!

Código para crear las pestañas,

// For each of the sections in the app, add a tab to the action bar. for (int i = 0; i < mCollectionPagerAdapter.getCount(); i++) { mActionBar.addTab(mActionBar.newTab() .setText(mGenres.get(i).getName()) .setTabListener(this)); //Let''s request the movies for the first three genres new GetMoviesByGenre().execute(mGenres.get(i).getId()); }

Cuando se selecciona una pestaña,

@Override public void onTabSelected(ActionBar.Tab tab, android.app.FragmentTransaction arg1) { //Let''s update the dataset for the selected genre TabFragment fragment = (TabFragment) getSupportFragmentManager().findFragmentByTag( "android:switcher:"+R.id.pager+":"+tab.getPosition()); if(fragment != null) // could be null if not instantiated yet { if(fragment.getView() != null) { fragment.updateDisplay(tab.getPosition()); // do what updates are required } } mViewPager.setCurrentItem(tab.getPosition()); }

Clase CollectionPageAdapter

public class CollectionPagerAdapter extends FragmentPagerAdapter { final int NUM_ITEMS = 3; // number of tabs List<Fragment> fragments = new ArrayList<Fragment>(); public Fragment getItem(int pos) { return fragments.get(pos); } public void addFragment(Fragment f) { fragments.add(f); } public CollectionPagerAdapter(FragmentManager fm) { super(fm); //Let''s add the fragments for (int i=0;i<NUM_ITEMS;i++) { Fragment fragment = new TabFragment(); Bundle args = new Bundle(); args.putInt(TabFragment.ARG_OBJECT, 0); fragment.setArguments(args); addFragment (fragment); } } @Override public int getCount() { return NUM_ITEMS; }

}

Clase TabFragment

public class TabFragment extends ListFragment { public static final String ARG_OBJECT = "object"; private MoviesAdapter m_Adapter; private ArrayList <Movie> mMovies = new ArrayList<Movie>(); @Override public void onActivityCreated(Bundle savedInstanceState) { super.onActivityCreated(savedInstanceState); // you only need to instantiate these the first time your fragment is // created; then, the method above will do the rest if (m_Adapter == null) { m_Adapter = new MoviesAdapter(getActivity(), mMovies); } setListAdapter(m_Adapter); } @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { int position = getArguments().getInt(ARG_OBJECT); // to check is the right fragment View rootView = inflater.inflate(R.layout.tabs, container, false); return rootView; } public void updateDisplay (int type) { GlobalVars gv = (GlobalVars)getActivity().getApplicationContext(); switch (type) { case 0: mMovies = gv.getActionMovies(); break; case 1: mMovies = gv.getAdventureMovies(); break; case 2: mMovies = gv.getAnimationMovies(); break; } m_Adapter.notifyDataSetChanged(); }

}

No hago lo que estoy haciendo mal, supongo que los fragmentos están en mal estado, porque cuando presiono la segunda pestaña, los datos de la primera pestaña se actualizan, y así sucesivamente ...

¡Gracias!


Estoy de acuerdo con Nirvik en esto, sin embargo, hay una mejora cruciual que debe hacerse. Esta implementación tiene un defecto: al pasar al próximo fragmento, se invoca el método onPageSelected, que a su vez invoca el métodoTabSelected llamando a mActionBar.setSelectedNavigationItem (position) ;. Esto causa un parpadeo en la animación. Esta:

viewPager.setCurrentItem(i);

debe ser reemplazado por esto:

if(i != viewPager.getCurrentItem()) { viewPager.setCurrentItem(i); }

dando como resultado una transición suave.


¡En lugar de usar CollectionPageAdapter, cambié para usar la clase TabsAdapter que se muestra en la documentación de ViewPager de Android y funciona!

public class TabsAdapter extends FragmentPagerAdapter implements ActionBar.TabListener, ViewPager.OnPageChangeListener { private final Context mContext; private final ActionBar mActionBar; private final ViewPager mViewPager; private final ArrayList<TabInfo> mTabs = new ArrayList<TabInfo>(); private final List<Fragment> fragments = new ArrayList<Fragment>(); static final class TabInfo { private final Class<?> clss; private final Bundle args; TabInfo(Class<?> _class, Bundle _args) { clss = _class; args = _args; } } public TabsAdapter(FragmentActivity activity, ViewPager pager) { super(activity.getSupportFragmentManager()); mContext = activity; mActionBar = activity.getActionBar(); 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 int getItemPosition(Object object) { return POSITION_NONE; } @Override public Fragment getItem(int position) { TabInfo info = mTabs.get(position); Fragment fr = Fragment.instantiate(mContext, info.clss.getName(), info.args); //addFragment (fr, position); return fr; } public void addFragment(Fragment f, int location) { if (fragments.size() == 0) fragments.add(f); else fragments.add(location, f); } @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { } @Override public void onPageSelected(int position) { mActionBar.setSelectedNavigationItem(position); } @Override public void onPageScrollStateChanged(int state) { } @Override public void onTabSelected(Tab tab, android.app.FragmentTransaction ft) { Object tag = tab.getTag(); for (int i=0; i<mTabs.size(); i++) { if (mTabs.get(i) == tag) { updateDatasetMovies (i); mViewPager.setCurrentItem(i); } } } @Override public void onTabReselected(Tab tab, android.app.FragmentTransaction ft) { // TODO Auto-generated method stub } @Override public void onTabUnselected(Tab tab, android.app.FragmentTransaction ft) { // TODO Auto-generated method stub } public void updateDatasetMovies (int pos) { //Let''s update the dataset for the selected genre TabFragment fragment = (TabFragment) ((FragmentActivity)mContext).getSupportFragmentManager().findFragmentByTag( "android:switcher:"+R.id.pager+":"+pos); //TabFragment fragment = (TabFragment) getItem(pos); if(fragment != null) // could be null if not instantiated yet { if(fragment.getView() != null) { // no need to call if fragment''s onDestroyView() //has since been called. fragment.updateDisplay(pos); // do what updates are required } } }

} `