Подтвердить что ты не робот

Добавление/удаление страниц в ViewPager динамически

Я хотел бы добавить или удалить страницы из моего пейджера просмотра динамически. Возможно ли это?

4b9b3361

Ответ 1

Да, поскольку ViewPager получает дочерние представления из PagerAdapter, вы можете добавлять к нему новые страницы/удалять страницы и вызывать .notifyDataSetChanged(), чтобы перезагрузить его.

Ответ 2

Да. Вы можете динамически добавлять или удалять представления в PagerAdapter, который передает их в ViewPager, и вызывать notifyDataSetChanged() из PagerAdapter, чтобы предупредить затронутый ViewPager об изменениях. Однако, когда вы это делаете, вы должны переопределить getItemPosition(Object) PagerAdapter, который сообщает им, изменились ли позиции, которые они сейчас показывают, изменили позиции. По умолчанию эта функция установлена ​​на POSITION_UNCHANGED, поэтому ViewPager не будет обновляться немедленно, если вы не переопределите этот метод. Например,

public class mAdapter extends PagerAdapter {
    List<View> mlist;

    public void addView(View view, int index) {
        mList.add(index, view);
        notifyDataSetChanged();
    }

    public void removeView(int index) {
        mList.remove(index);
        notifyDataSetChanged();
    }

    @Override
    public int getItemPosition(Object object) {
        if (mList.contains((View) object) {
            return mList.indexOf((View) object);
        } else {
            return POSITION_NONE;
        }
    }
}

Хотя, если вы просто хотите временно добавить или удалить представление с дисплея, но не из набора данных PagerAdapter, попробуйте использовать setPrimaryItem(ViewGroup, int, Object) для перехода к определенному представлению в данных PagerAdapter и destroyItem(ViewGroup, int, Object) для удаления вид с дисплея.

Ответ 3

Да, код должен выглядеть следующим образом:

public int addPage(View view, int position) {
        if ((position >= 0) && (position < getSize())) {
            myPagerAdapter.mListViews.add(position, view);
            myPagerAdapter.notifyDataSetChanged();
            return position;
        } else {
            return -1;
        }
    }

public View removePage(int position) {
        if ((position < 0) || (position >= getSize()) || (getSize()<=1)) {
            return null;
        } else {
            if (position == mPager.getCurrentItem()) {
                if(position == (getSize()-1)) {
                    mPager.setCurrentItem(position-1);
                } else if (position == 0){
                    mPager.setCurrentItem(1);
                }
            }
            View tempView = myPagerAdapter.mListViews.remove(position);
            myPagerAdapter.notifyDataSetChanged();
            return tempView;
        }
    }

Но есть ошибка. Если текущий элемент равен 0, и для удаления страницы 0 он не будет обновлять экран мгновенно, я не нашел для этого решения.

Ответ 4

Я уверен, что вы создали адаптер, расширив PageAdapter, поэтому существует один метод:

 @Override
 public void destroyItem(View collection, int position, Object view) {
           ((ViewPager) collection).removeView((View) view);
 }

Для более подробного примера для этого просто перейдите этот пример.

Ответ 5

Здесь альтернативное решение этого вопроса. Мой адаптер:

private class PagerAdapter extends FragmentPagerAdapter implements 
              ViewPager.OnPageChangeListener, TabListener {

    private List<Fragment> mFragments = new ArrayList<Fragment>();
    private ViewPager mPager;
    private ActionBar mActionBar;

    private Fragment mPrimaryItem;

    public PagerAdapter(FragmentManager fm, ViewPager vp, ActionBar ab) {
        super(fm);
        mPager = vp;
        mPager.setAdapter(this);
        mPager.setOnPageChangeListener(this);
        mActionBar = ab;
    }

    public void addTab(PartListFragment frag) {
        mFragments.add(frag);
        mActionBar.addTab(mActionBar.newTab().setTabListener(this).
                            setText(frag.getPartCategory()));
    }

    @Override
    public Fragment getItem(int position) {
        return mFragments.get(position);
    }

    @Override
    public int getCount() {
        return mFragments.size();
    }

    /** (non-Javadoc)
     * @see android.support.v4.app.FragmentStatePagerAdapter#setPrimaryItem(android.view.ViewGroup, int, java.lang.Object)
     */
    @Override
    public void setPrimaryItem(ViewGroup container, int position,
            Object object) {
        super.setPrimaryItem(container, position, object);
        mPrimaryItem = (Fragment) object;
    }

    /** (non-Javadoc)
     * @see android.support.v4.view.PagerAdapter#getItemPosition(java.lang.Object)
     */
    @Override
    public int getItemPosition(Object object) {
        if (object == mPrimaryItem) {
            return POSITION_UNCHANGED;
        }
        return POSITION_NONE;
    }

    @Override
    public void onTabSelected(Tab tab, FragmentTransaction ft) {
        mPager.setCurrentItem(tab.getPosition());
    }

    @Override
    public void onTabUnselected(Tab tab, FragmentTransaction ft) { }

    @Override
    public void onTabReselected(Tab tab, FragmentTransaction ft) { }

    @Override
    public void onPageScrollStateChanged(int arg0) { }

    @Override
    public void onPageScrolled(int arg0, float arg1, int arg2) { }

    @Override
    public void onPageSelected(int position) {
        mActionBar.setSelectedNavigationItem(position);
    }

    /**
     * This method removes the pages from ViewPager
     */
    public void removePages() {
        mActionBar.removeAllTabs();

                    //call to ViewPage to remove the pages
        vp.removeAllViews();
        mFragments.clear();

        //make this to update the pager
        vp.setAdapter(null);
        vp.setAdapter(pagerAdapter);
    }
}

Код для удаления и добавления динамически

//remove the pages. basically call to method removeAllViews from ViewPager
pagerAdapter.removePages();

pagerAdapter.addPage(pass your fragment);

После совета Peri Hartman он начал работать после того, как я установил null в адаптер ViewPager и снова установил адаптер после удаления просмотров. До этого страница 0 не отображает содержимое списка.

Ответ 6

Сначала: переопределить метод pagerAdapter "getItemPosition"

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

Во-вторых: удалите привязку данных с помощью адаптера. и call adapter.notifydatachanged

Ответ 7

@Bind(R.id.pager)
ViewPager pager;
int pos = pager.getCurrentItem();
pager.removeViewAt(pos);

Ответ 8

Это решение работает до сих пор:

 public class CustomPagerAdapter extends PagerAdapter {

    private final List<Item> objects = new ArrayList<>();

    public CustomPagerAdapter(List<Item> objects) {
        if (objects != null) {
            this.objects.add(objects);
        }
    }

    @Override
    public int getCount() {
        return objects.size();
    }

    @Override
    public boolean isViewFromObject(View view, Object object) {
        Item item = (Item) object;
        ItemView itemView = (ItemView) view;
        return Objects.equals(itemView.getItem(), item);
    }

    @Override
    public int getItemPosition(Object object) {
        Item item = (Item) object;
        int idx = objects.indexOf(item);
        return idx == -1 ? POSITION_NONE : idx;
    }

    @Override
    public Item instantiateItem(ViewGroup container, int position) {
        Item item = objects.get(position);

        final int id = generateViewIdForItem(item);
        ItemView itemView = new ItemView(container.getContext());
        itemView.setId(id);
        container.addView(itemView);

        itemView.setItem(item);

        return item;
    }

    @Override
    public void destroyItem(ViewGroup container, int position, Object object) {
        Item item = (Item) object;
        final int id = generateViewIdForItem(item);
        View view = container.findViewById(id);
        if (view != null) {
            container.removeView(view);
        }
    }

    public void update(@Nullable List<Item> objects) {
        this.objects.clear();
        if (objects != null) {
            this.objects.addAll(objects);
        }
        notifyDataSetChanged();
    }

    public void clear() {
        update(null);
    }

    /* add remove/update/add methods if you need, don't forget to call notifyDataSetChanged */

    private static int generateViewIdForItem(Item item) {
        return Math.abs(item.hashCode());
    }
}

Обратите внимание:

  • Ваш класс Item должен содержать соответствующую реализацию для методов equals и hashCode
  • Ваш класс ItemView должен содержать getter и setter для вашего объекта Item.